背景
開發新項目,寫Swager的mode的時候用到了嵌套Model,因而在代碼中,出現了靜態內部類。在codeReview的時候稍微和你們聊了一下。尤爲是Static 修飾類和修飾對象和變量不同呢?java
定義
1. 內部類
- 能夠將一個類的定義放在另外一個類的定義內部,這就是內部類;
- 嵌套類是其封閉類的成員。非靜態嵌套類(內部類)能夠訪問封閉類的其餘成員,即便它們被聲明爲私有的也是如此。靜態嵌套類無權訪問封閉類的其餘成員。爲一體的一個部件OuterClass,一個嵌套類能夠聲明private,public,protected,或包專用。(回想一下,只能聲明外部類public或將其包裝爲私有。)
2. 靜態內部類
- 再一個普通類裏面,給內部類加上static關鍵字的修飾;
- 與類方法和變量同樣,靜態嵌套類與其外部類相關聯。與靜態類方法同樣,靜態嵌套類不能直接引用其封閉類中定義的實例變量或方法:它只能經過對象引用來使用它們。(就和兩個普通不一樣的類之間的使用)
3. 二者的區別
- 內部類只是外部類的成員變量,通俗講,就是你只能經過先調用外部類才能去拿到這個類(可是這是和組合仍是有區別的)。
- 可是靜態內部類就像是一個普通類同樣。能夠直接調用,直接去new對象。
4. Java 擁有嵌套類有什麼做用呢?
- 這是一種對僅在一個地方使用的類進行邏輯分組的方法:若是一個類僅對另外一個類有用,那麼將其嵌入該類並將二者保持在一塊兒是合乎邏輯的。嵌套此類「幫助程序類」可以使它們的程序包更加簡化。
- 它增長了封裝:考慮兩個頂級類A和B,其中B須要訪問A的成員,不然將對其進行聲明private。經過將類B隱藏在類A中,能夠將A的成員聲明爲私有,而B能夠訪問它們。另外,B自己能夠對外界隱藏。
- 這可能會致使代碼更具可讀性和可維護性:在頂級類中嵌套小類會使代碼更靠近使用位置。
Demo
- talk is cheap ,Show me Code;
package 靜態內部類; import com.sun.tools.internal.xjc.reader.xmlschema.bindinfo.BIConversion; import javassist.runtime.Inner; import lombok.Data; /** * @authoryuanxindong * @date: 2020/6/19 10:25 下午 */ @Data public class OuterClassDemo { String outerStr; public OuterClassDemo(String outerStr) { this.outerStr = outerStr; } @Data public static class StaticInnerClass{ public StaticInnerClass(String innerStr) { this.innerStr = innerStr; } private String innerStr; } @Data public class InnerClass{ private String innerClassStr; public InnerClass(String outerStr) { //能夠和外部類通信 this.innerClassStr = getOuterStr(); } } public static void main(String[] args) { OuterClassDemo staticClassDemo =new OuterClassDemo("Outer"); staticClassDemo.getOuterStr(); // 內部正常類是不能直接new出來的 // OuterClass outerClass = new OuterClass(); StaticInnerClass innerClass = new StaticInnerClass("StaticInner"); System.out.println(innerClass.getInnerStr()); initInnerClass(); } public static void initInnerClass(){ OuterClassDemo staticClassDemo1 = new OuterClassDemo("OuterClassDemo"); InnerClass innerClass = staticClassDemo1.new InnerClass("outerStr"); System.out.println(innerClass.getInnerClassStr()); } }
注意事項
- 序列化強烈建議不要對內部類(包括 本地和 匿名類)進行序列化。當Java編譯器編譯某些構造(例如內部類)時,它會建立綜合構造。
- 這些是類,方法,字段以及其餘在源代碼中沒有相應構造的構造。合成構造使Java編譯器無需更改JVM就能夠實現新的Java語言功能。可是,合成構造在不一樣的Java編譯器實現中可能有所不一樣,這意味着.class文件在不一樣的實現中也可能有所不一樣。所以,若是序列化一個內部類,而後使用其餘JRE實現對其進行反序列化,則可能會遇到兼容性問題。
核心討論
- 瞭解了靜態內部類後,那static爲何修飾了類,對於這個類也是起了一個全局可用的一個做用?
- 越想問題越多,還有就是爲何被Static 修飾的方法能夠被類直接引用到?而static 修飾的類也能夠被其餘的類直接使用,而不依賴於對象。
答 :咱們得明確一下json
- static修飾類的方法,表示這個方法和這個類對象沒有關係,只是和這個類有關係
- static 修飾變量,按照是否靜態的對類成員變量進行分類可分兩種:一種是被static修飾的變量,叫靜態變量或類變量;另外一種是沒有被static修飾的變量,叫實例變量。二者的區別是:
- 對於靜態變量在內存中只有一個拷貝(節省內存),JVM只爲靜態分配一次內存,在加載類的過程當中完成靜態變量的內存分配,可用類名直接訪問(方便),固然也能夠經過對象來訪問(可是這是不推薦的)。
- 好的,是這樣的。static修飾對象 能夠全局使用,修飾方法能夠不依賴於對象,修飾類,也不用依賴與他的對象,也能夠被其餘的類直接使用,或者本身進行初始化。
總結
- 嵌套類:內部類和靜態內部類
- 內部類屬於外部類的成員,必須依賴與外部對象來實現,靜態內部類,不依賴,能夠本身單獨實現。
- static 的修飾 變量,類,方法,代碼塊。 共性全局性。變量的話也就是全劇惟一性,會出現多個飲用,但不會出現多個存儲。