<rp id="wnpn7"><ruby id="wnpn7"></ruby></rp>
<progress id="wnpn7"><track id="wnpn7"><rt id="wnpn7"></rt></track></progress>
<ruby id="wnpn7"></ruby>
<ruby id="wnpn7"><blockquote id="wnpn7"><div id="wnpn7"></div></blockquote></ruby>

    1. <em id="wnpn7"><ruby id="wnpn7"><input id="wnpn7"></input></ruby></em>
      1. <button id="wnpn7"><acronym id="wnpn7"></acronym></button><button id="wnpn7"><acronym id="wnpn7"></acronym></button>

        <rp id="wnpn7"><acronym id="wnpn7"></acronym></rp>

        <li id="wnpn7"><object id="wnpn7"><u id="wnpn7"></u></object></li>
        VB.net 2010 視頻教程 VB.net 2010 視頻教程 python基礎視頻教程
        SQL Server 2008 視頻教程 c#入門經典教程 Visual Basic從門到精通視頻教程
        當前位置:
        首頁 > 編程開發 > Java教程 >
        • java入門之如何優雅地打印一個Java對象?

        你好呀,我是沉默王二,一個和黃家駒一樣身高,和劉德華一樣顏值的程序員。雖然已經寫了十多年的 Java 代碼,但仍然覺得自己是個菜鳥(請允許我慚愧一下)。

        在一個月黑風高的夜晚,我思前想后,覺得再也不能這么蹉跎下去了。于是痛下決心,準備通過輸出的方式倒逼輸入,以此來修煉自己的內功,從而進階成為一名真正意義上的大神。與此同時,希望這些文章能夠幫助到更多的讀者,讓大家在學習的路上不再寂寞、空虛和冷。

        為了更好的輸入,我選擇 Stack Overflow 作為戰斗的第一線,畢竟很多前輩都在強烈推薦。本篇文章,我們來探討一下如何優雅地打印一個Java對象。

        真沒想到,這個問題的訪問量像阿爾泰山一樣高,訪問量足足有 29+ 萬次,這不得了啊!說明有很多很多的程序員被這個問題困擾過。

        來回顧一下提問者的問題吧。

        提問者定義了這樣一個類:

        public class Cmower {
            private String name;
        
            public Cmower(String name) {
                this.name = name;
            }
        
            public String getName() {
                return name;
            }
        
            public void setName(String name) {
                this.name = name;
            }
        }
        

        然后創建了一個該類的對象,并嘗試打印它:

        Cmower cmower = new Cmower("沉默王二");
        System.out.println(cmower);
        

        但是輸出的結果并不是他想要的:

        com.cmower.java_demo.stackoverflow.printObject.Cmower@355da254
        

        除此之外,他在打印數組的時候也出現了相似的問題:

        Cmower [] cmowers = {new Cmower("沉默王二"), new Cmower("沉默王三")};
        System.out.println(cmowers);
        

        輸出結果為:

        [Lcom.cmower.java_demo.stackoverflow.printObject.Cmower;@4dc63996
        

        Cmower@355da254 和 [LCmower;@4dc63996 這樣的輸出結果代表著什么意思呢?怎么樣才能把 Cmower 類的 name 打印出來呢?以及如何打印一個對象的列表(數組或者集合)呢?

        如果大家也被這樣的問題困擾過,或者正在被困擾,就請隨我來,咱們肩并肩手拉手一起梳理一下這個問題,并找出最佳答案。Duang、Duang、Duang,打怪進階嘍!

        01、究竟發生了什么?

        所有的 Java 對象都默認附帶了一個 toString() 的方法,當我們嘗試打印這個對象的時候,該方法就會被調用。

        System.out.println(object);  // 調用 object.toString()
        

        toString() 方法由 Object 類(所有 Java 對象的超類)定義,該方法會返回一個看起來晦澀難懂的字符串:

        1)Class 名,由包名和類名組成,比如 com.Cmower
        2)@ 連接符;
        3)十六進制的哈希碼。

        來看一下該方法的源碼:

        public String toString() {
            return getClass().getName() + "@" + Integer.toHexString(hashCode());
        }
        

        數組和普通的 Java 對象類似,只有一點點不同——追蹤 Class 類的 getName() 方法就可以印證這一點。

        If this class object represents a class of arrays, then the internal form of the name consists of the name of the element type preceded by one or more '[' characters representing the depth of the array nesting.

        大致的意思就是,如果是一個數組的話,Class 名的前面會有一個或者多個英文中括號“[”,表示數組的維度(一維數組為一個“[”,二維數組為兩個“[”),然后再緊跟一個元素的類型首字母。

        這就是為什么對象數組的前綴是“[L”的原因。是不是有一種恍然大悟的感覺?

        02、自定義輸出

        如果想在打印的時候輸出自己預期的結果,就必須在自定義類中重寫 toString() 方法,來看例子。

        public class Cmower {
            private String name;
            // 省略構造方法和 getter/setter
        
            @Override
            public String toString() {
                return name;
            }
        }
        

        當我們再次打印 Cmower 對象時,輸出結果就不再是 com.Cmower@355da254 了。

        沉默王二
        

        但是這樣的結果并不會令我們滿意,它有些突兀,沒法表示對象的類型。更優雅的做法是這樣的:

        public class Cmower {
            private String name;
            // 省略構造方法和 getter/setter
        
            @Override
            public String toString() {
                return getClass().getSimpleName() + "[name=" + name + "]";
            }
        }
        

        再次打印 Cmower 對象,輸出結果為:

        Cmower[name=沉默王二]
        

        這樣的形式不僅看起來美觀,還能夠在調試的時候給出有用的信息。但是,有時候我們不想重寫 toString()方法(想保留原有的打印格式 ClassType@123121),又想打印該對象的信息,那么最好定義一個新的方法,比如說 toMyString() 方法。

        03、自動化輸出

        IDE(Eclipse 或者 Intellj IDEA) 通常會提供一種針對類的字段的輸出格式,用來覆蓋 toString() 方法。

        @Override
        public String toString() {
            return "Cmower{" +
                    "name='" + name + '\'' +
                    '}';
        }
        

        另外,一些開源的第三方類庫也會提供這樣的功能,比如說:

        1)Apache Commons Lang 的 ToStringBuilder。

        使用方法:

        @Override
        public String toString() {
            return ToStringBuilder.reflectionToString(this);
        }
        

        輸出結果:

        com.cmower.printObject.Cmower@355da254[name=沉默王二]
        

        2)Google Guava 的 MoreObjects

        使用方法:

        @Override
        public String toString() {
            return MoreObjects.toStringHelper(this)
                    .add("name", getName())
                    .toString();
        }
        

        輸出結果:

        Cmower{name=沉默王二}
        

        3)Lombok 的 @toString 注解(IDE 需要先安裝 Lombok 的插件)

        使用方法:

        @ToString
        public class Cmower {
        
            private String name;
        
            // 省略構造方法和 getter/setter
        }
        

        只需要一個 @toString 注解,不需要覆蓋 toString() 方法。

        輸出結果:

        Cmower(name=沉默王二)
        

        04、打印對象列表(數組或者集合)

        上述內容已經把打印單個對象的事情嘮明白了,are you ok?接下來,我們來說道說道打印對象列表的事兒。

        1)數組

        Arrays.toString() 可以將任意類型的數組轉成字符串,包括基本類型數組和引用類型數組。代碼示例如下。

        Cmower[] cmowers = {new Cmower("沉默王二"), new Cmower("沉默王三")};
        System.out.println(Arrays.toString(cmowers));
        

        輸出結果:

        [Cmower{name='沉默王二'}, Cmower{name='沉默王三'}]
        

        2)集合

        對于集合來說,可以直接打印就能輸出我們預期的結果。代碼示例如下。

        List<Cmower> list = new ArrayList<>();
        list.add(new Cmower("沉默王二"));
        list.add(new Cmower("沉默王三"));
        System.out.println(list);
        

        輸出結果:

        [Cmower{name='沉默王二'}, Cmower{name='沉默王三'}]
        

        05、鳴謝

        好了,我親愛的讀者朋友,以上就是本文的全部內容了。能在疫情期間堅持看技術文,二哥必須要伸出大拇指為你點個贊

        相關教程
                
        免费看成年人视频大全_免费看成年人视频在线观看