內部類,java類庫常常使用的一種形式,此次有時間,記載一下,如下全是代碼,描述全在註釋當中,能夠直接複製代碼,進行測試java
----------------------------------我是分割線------------------------------------ide
public class InnerClass { private String msg = "外部類private修飾的字符串"; public String msg1 = "外部類public修飾的字符串"; static int number = 0; final double d = 1.2d; static final float F = 1.3f; /** 普通的內部類; 限制跟使用以下: 1:內部類可使用外部類的全局變量 2:內部類內,不能定義靜態方法跟靜態變量,由於內部類是依賴外部類存在的 只有實例化外部類了,JVM纔會去加載內部類, 而靜態方法跟靜態變量都是依賴類存在的, 3:當內部類修改了外部類的全局變量,外部類的全局變量也會被修改 4:內部類中,不容許在定義靜態內部類,可是能夠接着定義非靜態內部類 5:內部類也能夠繼承,實現接口 */ public class RuleInnerClass{ /* 可是能夠定義普通的內部類 */ class InnerInnerClass{ } /* 內部內中,不容許定義靜態內部類 */ //static class StaticInnerClass{ // //} /* * 編譯器會報錯,普通內部類不容許定義靜態變量 */ //static int a = 0; /* 也不容許定義靜態方法 */ //public static void printmsg(){ // //} public void print(){ System.out.println(msg); System.out.println(msg1); System.out.println(number); System.out.println(d); System.out.println(F); } /** 構建私有內部類實例,調用其方法 */ public void printPrivateInnerClass(){ PrivateInnerClass privateInnerClass = new PrivateInnerClass(); privateInnerClass.print(); } } /** 私有內部類的功能限制跟普通內部類同樣 不過私有的內部類,不能在外部類之外進行實例化 */ private class PrivateInnerClass{ public void print(){ System.out.println(msg); System.out.println(msg1); System.out.println(number); System.out.println(d); System.out.println(F); } } /** 靜態內部類; 限制跟使用以下: 1:靜態內部類只能使用外部類的靜態變量 2:靜態內部類內,能夠定義非靜態變量跟靜態變量以及靜態方法,由於靜態內部類不依賴於外部類的實例 3:靜態內部類也能夠實現接口,跟繼承類 4:靜態內部類內部,還能夠定義靜態內部類跟非靜態內部類 */ static class StaticInnerClass implements Contents{ int a = 0; static int i = 1; class IsNotStaticInnerInnerClass{ } static class StaticInnerInnerClass{ } public static void printStatic(){ System.out.println("靜態內部類的靜態方法"); } public void print(){ /* 靜態內部類裏面,不容許調用外部類的非靜態變量 */ //System.out.println(msg); System.out.println(number); System.out.println(F); System.out.println(a); System.out.println(i); } } /** * 局部內部類限制跟普通內部類差很少 * 1:都是不能定義靜態屬性跟方法也不能定義靜態內部類 * 2:局部內部類能夠調用外部類的全部全局變量 * 3:局部內部類的內部類能夠定義普通局部內部類 * 4:局部內部類調用局部變量,必須是final修飾的,由於局部變量在方法調用結束就會銷燬,可是局部內部類不會銷燬 * 5:局部內部類能夠繼承跟實現接口 * 6:局部內部類不能當作返回參數返回,若是要返回局部內部類,實現一個接口或者繼承一個類,經過向上轉型返回 * 7:方法外局部內部類引用,只能經過繼承類或者實現接口向上轉型返回,由於局部內部類的做用域只能限於方法內,因此不能再方法外進行實例化 */ public Contents getLocalInnerClass(){ final String methodFiled = "局部變量"; /* 不能定義一個局部靜態類 */ //static class LocalInnerStaticClass{ // //} /* 局部內部類,不能使用修飾符 */ class LocalInnerClass implements Contents{ int localMenthodFiled = 0; /* 不能定義靜態變量 */ //static int a = 0; public void print(){ System.out.println(localMenthodFiled); System.out.println(number); System.out.println(msg); System.out.println(methodFiled); } /* 局部內部類也不能定義靜態方法 */ //public static void staticPrint(){ // //} /* 也不能定義靜態內部類 */ //static class LocalStaticClass{ // //} } return new LocalInnerClass(); } /** * 匿名內部類限制跟局部內部類差很少 * 1:都是不能定義靜態屬性跟方法也不能定義靜態內部類 * 2:匿名內部類能夠調用外部類的全部全局變量 * 3:匿名內部類的內部類能夠定義普通局部內部類 * 4:匿名內部類調用局部變量,必須是final修飾的,由於局部變量在方法調用結束就會銷燬,可是匿名內部類不會銷燬 * 5:匿名必須實現一個接口,或者集成一個類 * 6:匿名內部類不能當作返回參數返回(由於它壓根就沒名字),可是能夠返回匿名內部類實現的接口或者繼承類,從而返回匿名內部類的引用 */ public Contents getContents(){ final int w = 1; return new Contents() { int q = 0; /* 不能定義靜態變量 */ //static int s = 2; @Override public void print() { /* 能夠調用外部類的全部變量 */ System.out.println(msg); System.out.println(msg1); System.out.println(number); System.out.println(d); System.out.println(F); /* 調用局部變量,必須是final修飾 */ System.out.println(w); System.out.println(q); System.out.println("我是匿名內部類"); } /* 不能定義靜態方法 */ //public static void staticPrint(){ // //} /* 不能定義靜態內部類 */ //static class StaticClass{ // //} /* 能夠定義非靜態內部類 */ class IsNotStaticClass{ } }; } }
public class InnerTest { public static void main(String[] args) throws ClassNotFoundException, IllegalAccessException, InstantiationException, NoSuchMethodException, InvocationTargetException { InnerClass innerClass = new InnerClass(); /* 常規內部類構建方法有兩種 1: 是經過外部類.new 內部類類名來建立 2: 是經過反射建立 */ /** * 普通建立內部類的方法 */ InnerClass.RuleInnerClass ruleInnerClass = innerClass.new RuleInnerClass(); ruleInnerClass.print(); System.out.println("--------------------------------------"); ruleInnerClass.printPrivateInnerClass(); /** * 反射建立內部類的方法 * 須要注意的是,經過反射建立內部類,地址是報名.外部類類名$內部類類名 * 並且構建內部類,須要傳入一個外部類的引用, * 因此必須經過Constructor類的newInstance方法構建內部類 */ Class c =Class.forName("com.demo.innerClass.InnerClass$RuleInnerClass"); System.out.println("我須要一個外部對象:"+ Arrays.toString(c.getDeclaredConstructors())); Constructor constructor = c.getConstructor(InnerClass.class); InnerClass.RuleInnerClass o = (InnerClass.RuleInnerClass)constructor.newInstance(new InnerClass()); o.print(); System.out.println("--------------------------------------"); /* 建立靜態內部類,不須要外部類的實例,能夠經過 new 外部類.靜態內部類進行建立 調用靜態內部類的靜態方法,是經過 外部類.靜態內部類.靜態方法就能夠調用 調用靜態內部類的靜態變量,同理,只不過是把靜態方法,變爲靜態變量 */ InnerClass.StaticInnerClass staticInnerClass = new InnerClass.StaticInnerClass(); staticInnerClass.print(); InnerClass.StaticInnerClass.printStatic(); System.out.println("--------------------------------------"); /* 方法外建立局部內部類,只能經過繼承類或者實現接口向上轉型返回 由於局部內部類的做用域只能限於方法內 */ Contents contents = innerClass.getLocalInnerClass(); contents.print(); System.out.println("--------------------------------------"); /* 匿名內部類,只能經過向上轉型返回它的實例引用 */ Contents contents1 = innerClass.getContents(); contents1.print(); } }
到這,文章就結束了!測試
以上,均爲本人測試而得出的結果,可能會有出入,或者錯誤,歡迎指正code
歡迎轉載,請註明出處跟做者,謝謝!對象