您好,登錄后才能下訂單哦!
1. 什么是靜態內部類
在Java中有靜態代碼塊、靜態變量、靜態方法,當然也有靜態類,但Java中的靜態類只能是Java的內部類,也稱為靜態嵌套類。靜態內部類的定義如下:
public class OuterClass { static class StaticInnerClass { ... } }
在介紹靜態內部類之前,首先要弄清楚靜態內部類與Java其它內部類的區別。
2. 內部類
什么是內部類?將一個類的定義放在另一個類的內部,就是內部類。Java的內部類主要分為成員內部類、局部內部類、匿名內部類、靜態內部類。
2.1 成員內部類
成員內部類是最普通的內部類,就是一個普通的類定義在另一個類的內部,形式如下:
public class OuterClass { class InnerClass { ... } }
注:
在成員內部類中,可以直接訪問外部類的屬性、方法,即使是private類型也可以訪問,這是因為內部類持有一個外部類的引用,可以自由訪問。
成員內部類中不能存在任何靜態變量和靜態方法。
成員內部類是依附于外部類的,只有先創建了外部類才能夠創建內部類。
成員內部類的創建形式如下:
//定義成員內部類的方式一 OuterClass test = new OuterClass(); InnerClass innerA = test.new InnerClass(); //定義成員內部類的方式二 OuterClass.InnerClass innerB = new OuterClass().new InnerClass();
2.2 局部內部類
局部內部類是定義在一個方法或者一個作用域里面的類,形式如下:
public void methodInnerClass() { class InnerClass { ... } InnerClass A = new InnerClass(); }
注:
局部內部類就像是方法里面的一個局部變量一樣,不能有public、protected、private以及static修飾符。
可以直接訪問外部類的屬性、方法,即使是private類型也可以訪問。
2.3 匿名內部類
用過Swing的人應該對匿名內部類非常熟悉,Swing中使用了大量的匿名內部類。匿名內部類的形式如下:
Button button = new Button(); button.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent e) { ... } });
注:
匿名內部類沒有名字,沒有構造方法。
匿名內部類用于繼承其他類或是實現接口,并不需要增加額外的方法,只是對繼承方法的實現或是重寫。
2.4 靜態內部類
靜態內部類也是定義在另一個類里面的類,只不過在類的前面多了一個關鍵字static。其定義形式如下:
public class OuterClass { static class StaticInnerClass { ... } }
注:
靜態內部類的創建不依賴外部類。
靜態內部類不能訪問外部類的非靜態成員和非靜態方法。
2.5 靜態內部類與其它內部類的區別
靜態內部類與其它內部類最大的區別在于非靜態內部類在編譯完成之后會隱含地保存一個引用,該引用是指向創建它的外部類,但是靜態內部類卻沒有。靜態內部類只是嵌套在外部類中,因此也被稱為嵌套內部類。
2.6 為什么要使用內部類
方便將存在一定邏輯關系的類組織在一起,又可以對外界隱藏。
典型的情況是,內部類繼承自某個類或實現某個接口,內部類的代碼操作創建外部類的對象。典型的情況是Effective Java 2.0中Item 2講述的構建器模式。
使用內部類最吸引人的原因是:每個內部類都能獨立地繼承自一個(接口的)實現,所以無論外圍類是否已經繼承了某個(接口的)實現,對于內部類都沒有影響。如果沒有內部類提供的可以繼承多個具體的或抽象的類的能力,一些設計與編程問題就很難解決。從這個角度看,內部類使得多重繼承的解決方案變得完整。接口解決了部分問題,而內部類有效地實現了“多重繼承”。
3. 為什么要使用靜態內部類
使用靜態內部類主要是因為靜態內部類的兩個優點:
增強了類的封裝性
提高了代碼的可讀性
以下面的例子為例:將Builder放在NutritionFacts的內部,說明二者之間有一定的關系,比起將兩個類分開要好很多,因此增強了類的封裝性。其次,二者放在一起,能很明顯的看出Builder類是用來創建NutritionFacts類的,提高了代碼的可讀性。
4. 靜態內部類的例子
靜態內部類的創建:
//Builder Pattern public class NutritionFacts { private final int servingSize; private final int servings; private final int calories; private final int fat; private final int sodium; private final int carbohydrate; public static class Builder { // Required parameters private final int servingSize; private final int servings; // Optional parameters - initialized to default values private int calories = 0; private int fat = 0; private int carbohydrate = 0; private int sodium = 0; public Builder(int servingSize, int servings) { this.servingSize = servingSize; this.servings = servings; } public Builder calories(int val) { calories = val; return this; } public Builder fat(int val) { fat = val; return this; } public Builder carbohydrate(int val) { carbohydrate = val; return this; } public Builder sodium(int val) { sodium = val; return this; } public NutritionFacts build() { return new NutritionFacts(this); } } private NutritionFacts(Builder builder) { servingSize = builder.servingSize; servings = builder.servings; calories = builder.calories; fat = builder.fat; sodium = builder.sodium; carbohydrate = builder.carbohydrate; } }
靜態內部類的使用:
NutritionFacts cocaCola = new NutritionFacts.Builder(240, 8).calories(100).sodium(35).carbohydrate(27).build();
總結
以上就是本文關于Java中的靜態內部類詳解及代碼示例的全部內容,希望對大家有所幫助。感興趣的朋友可以繼續參閱本站:Java編程子類能否重寫父類的靜態方法探索、Java單例模式實現靜態內部類方法示例等,如有不足之處,歡迎留言指出。感謝朋友們對本站的支持!
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。