我們一般使用的java內(nèi)部類有4種形式:一般內(nèi)部類、局部內(nèi)部類、匿名內(nèi)部類、靜態(tài)內(nèi)部類。以下是我作的一個(gè)測試,以說明各種內(nèi)部類的特性。
有關(guān)內(nèi)部類的特性,代碼中有詳細(xì)說明,如下。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
|
/* * java內(nèi)部類測試 * * InterObj反射結(jié)果: * * private int i * private InterObj$InterA ia * public InterObj() * public static void main(java.lang.String[]) * private int getI() * public void p() * public void pi() * public void pp() * public static void ppp() * public void pppp() * 下面是編譯器自動(dòng)生成用于訪問私有屬性或方法package級(jí)別的static方法 * static int access$0(InterObj) */ public class InterObj { private int i=8; private InterA ia=null; public InterObj(){ ia=new InterA(); } private int getI(){ return i; } public void p(){ pi(); pp(); ppp(); pppp(); } /* * 在一般內(nèi)部類中可以訪問“外套類”中的任何級(jí)別的方法和屬性。而外套類也同樣可以 * 訪問“內(nèi)部類”中的任何級(jí)別的方法和屬性。因?yàn)閮?nèi)部類可以持有對外套類對象的引用。 * 而“外套類”對于自己的需要被內(nèi)部類訪問的私有方法和屬性,編譯器都會(huì)自動(dòng)生成與 * 私有方法和屬性相對應(yīng)的“package”級(jí)別的static方法,這些方法需要用外部類對象作 * 為參數(shù),這樣就可以在“package”級(jí)別的static方法中通過訪問外套類中的私有方法和 * 屬性了。 * 而對于外套類要訪問內(nèi)部類中的私有方法和屬性,也是同樣的原理,內(nèi)部類在編譯時(shí), * 會(huì)生成與需要被外套類訪問的私有方法、屬性相對應(yīng)的“package”級(jí)別的static方法。 * * InterA反射結(jié)果: * private int ia * 下面是內(nèi)部類持有的外套類對象引用 * final InterObj this$0 * 構(gòu)造函數(shù)中用外套類對象作為參數(shù) * InterObj$InterA(InterObj) * private void pA() * 下面是編譯器自動(dòng)生成用于訪問私有屬性或方法package級(jí)別的static方法 * static void access$0(InterObj$InterA) * public void pA1() * */ class InterA{ private int ia=9; private void pA(){ System.out.println("this is InterA.pA: ia="+ia+",InterObj.i="+getI()); } public void pA1(){ System.out.println("this is InterA.pA1: ia="+ia+",InterObj.i="+getI()); } } /* * 局部內(nèi)部類,只在方法內(nèi)部可見,其它特性與一般內(nèi)部類相同。 * 對需要訪問的局部變量,必需設(shè)置成final,因?yàn)榫植績?nèi)部類雖然可以持有對外套類對象的 * 引用來訪問外部類的屬性和方法,但是卻不能訪問外部類方法中局部變量,所有編譯器就 * 在局部內(nèi)部類中“拷貝”了一份需要訪問的局部變量(但是對于基本類型int,float和String * 等值不發(fā)生改變的類型沒有拷貝)為了保證拷貝的變量值和外部方法中的變量的值所指向的 * 對象是同一 個(gè)對象,所以要求那些被局部類使用的局部變量應(yīng)該設(shè)置成final,而不能被修 * 改,這樣來保證局部內(nèi)中拷貝的變量和外部方法中的變量所指向的是同一個(gè)對象。變量設(shè) * 置成final只是控制變量指向的對象地址不變,而不是它指向的對象的內(nèi)部屬性不能改變。 * * InterB的反射結(jié)果: * * private int ib * 下面是內(nèi)部類持有的外套類對象引用 * final InterObj this$0 * 下面是內(nèi)部類持有的外部方法中的局部變量Test對象的引用拷貝 * private final Test val$test * 構(gòu)造函數(shù)中用外套類對象和局部變量Test作為參數(shù) * InterObj$1$InterB(InterObj,Test) * private void pB() * 下面是編譯器自動(dòng)生成用于訪問私有屬性或方法package級(jí)別的static方法 * static void access$0(InterObj$1$InterB) */ public void pi(){ final int s=5; final Test test=new Test(); class InterB{ private int ib=7; private void pB(){ System.out.println("this is InterB.pB: ib="+ib+ ",(Method)pi.s="+s+",Test.t="+test.getT()); } } InterB ib=new InterB(); //此處改變了被局部內(nèi)部類引用了的Test test的內(nèi)部狀態(tài)。 //結(jié)果調(diào)用ib.pB()時(shí),輸出的就是改變后的值100 test.setT(100); ib.pB(); } /* * 靜態(tài)內(nèi)部類,在不需要持有對“外套類對象”的引用時(shí)使用。 * * InterC反射結(jié)果:(靜態(tài)內(nèi)部類沒有對外套類對象的引用) * private int ic * InterC() * private void pC() */ static class InterC{ private int ic=6; private void pC(){ System.out.println("this is InterC.pC: ic="+ic); } } /* * 非靜態(tài)方法,可以構(gòu)造靜態(tài)和非靜態(tài)的內(nèi)部類。 * 可以訪問內(nèi)部類中任何權(quán)限的屬性和方法 */ public void pp(){ InterA ia=new InterA(); ia.pA(); ia.pA1(); InterC ic=new InterC(); ic.pC(); //局部內(nèi)部類,只在方法內(nèi)部可見 //InterB ib=new InterB(); } /* * 靜態(tài)方法,只能構(gòu)造靜態(tài)的內(nèi)部類。 * 不能構(gòu)造非靜態(tài)的內(nèi)部類,因?yàn)殪o態(tài)方法中沒有this來引用“外套類”的對象,來構(gòu)造 * 需要引用外套類對象引用的內(nèi)部類對象。 */ public static void ppp(){ //InterA ia=new InterA(); //但是可以如下構(gòu)造: InterObj iobj=new InterObj(); InterA ia=iobj.new InterA(); ia.pA(); ia.pA1(); InterC ic=new InterC(); ic.pC(); //局部內(nèi)部類,只在方法內(nèi)部可見 //InterB ib=new InterB(); } /* * 匿名內(nèi)部類測試 */ public void pppp(){ TestInterface tif=new TestInterface(){ public void pppp() { System.out.println("TestInterface.noName"); } } ; tif.pppp(); } /* * 運(yùn)行結(jié)果: * this is InterB.pB: ib=7,(Method)pi.s=5,Test.t=100 * this is InterA.pA: ia=9,InterObj.i=8 * this is InterA.pA1: ia=9,InterObj.i=8 * this is InterC.pC: ic=6 * this is InterA.pA: ia=9,InterObj.i=8 * this is InterA.pA1: ia=9,InterObj.i=8 * this is InterC.pC: ic=6 * TestInterface.noName */ public static void main(String[] args) { InterObj io=new InterObj(); io.p(); } } /* * 用于創(chuàng)建內(nèi)部類的接口 */ interface TestInterface{ public void pppp(); } /* * 用于測試局部內(nèi)部類的局部變量類 */ class Test{ private int t= 9 ; public int getT(){ return t; } public void setT( int t1){ t=t1; } } |
再分享一則實(shí)例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
|
public class InnerClass { static Toy toy = new Toy(){ String name = "老吳" ; @Override public void jump() { System.out.println(name+ "跳出地球" ); go(); } public void go(){ System.out.println( "奔跑" ); } } ; /*內(nèi)部類:定義在類的內(nèi)部的類 *1.成員內(nèi)部類: *1.1成員內(nèi)部類可以直接訪問外部類的屬性 *1.2通過 外部類名.this 這種方式訪問外部類的當(dāng)前對象 *成員內(nèi)部類實(shí)例化對象: 外部類名.內(nèi)部類名 引用名 = 外部類對象.new 內(nèi)部類名(); *2.靜態(tài)內(nèi)部類 *2.1靜態(tài)內(nèi)部類內(nèi)部不能訪問外部類的成員資源,只能通過類名訪問外部類的靜態(tài)資源 *靜態(tài)內(nèi)部類實(shí)例化對象: 外部類名.內(nèi)部類名 引用名 = new 外部類名.內(nèi)部類名(); *3.局部內(nèi)部類: *3.1也可以直接訪問外部類的屬性 *3.2也可以通過 外部類名.this 訪問外部類當(dāng)前對象 *3.3局部內(nèi)部類只能在方法內(nèi)部被訪問,修飾符只能是默認(rèn)的 *4.匿名內(nèi)部類:在需要一個(gè)類的具體子類實(shí)例的時(shí)候,臨時(shí)的生成一個(gè)類使用 *new 類名(){ * 重寫方法; *}; *4.1匿名內(nèi)部類訪問外部方法的屬性,該屬性會(huì)被轉(zhuǎn)換為常量 *4.2匿名內(nèi)部類中新增的屬性和方法,只能在匿名內(nèi)部類內(nèi)部使用 * */ public static void main(String[] args) { Person per = new Person("老陳",18); Person.Computer pc = per.new Computer("外星人"); Person.Computer pc1 = new Person("簡自豪",18).new Computer("外星人"); pc.runGame(); pc1.runGame(); Person.Computer1 pc11 = new Person.Computer1("網(wǎng)吧的電腦"); pc11.runGame(); per.useComputer(); String str = "啦啦啦"; //str = "羅庫偶偶"; Computer com = new Computer(){ @Override public void runGame() { // TODO Auto-generated method stub System.out.println(per.age+"歲的"+per.name+"在玩啦啦啦啦啦德瑪西塔"); System.out.println(str); } } ; com.runGame(); //具體類的匿名內(nèi)部類獨(dú)享 /*Toy toy = new Toy(){ @Override public void jump() { System.out.println("跳出地球"); } };*/ toy.jump(); toy.jump(); //toy.go(); //System.out.println(toy.); } } class Person { String name; int age; static int age1 = 18 ; static String name1 = "全職高手" ; public Person(String name, int age) { super (); this .name = name; this .age = age; } public void playGame(){ System.out.println(name+ "玩游戲" ); } public class Computer{ String name; public Computer(String name) { super (); this .name = name; } public void runGame(){ System.out.println(name+ "運(yùn)行游戲" ); System.out.println(age+ "歲的" +Person. this .name+ "玩游戲" ); } } public static class Computer1{ String name; public Computer1(String name) { super (); this .name = name; } public void runGame(){ System.out.println(name+ "運(yùn)行游戲" ); System.out.println(Person.age1+ "的" +Person.name1+ "在玩游戲" ); } } public void useComputer(){ class Computer{ String name; public Computer(String name) { super (); this .name = name; } public void runGame(){ System.out.println(name+ "運(yùn)行游戲" ); System.out.println(Person. this .age+ "的" +Person. this .name+ "正在玩游戲" ); } } Computer com = new Computer( "筆記本" ); com.runGame(); } } public interface Computer { void runGame(); } public class Toy { public void jump(){ System.out.println( "玩具跳一下" ); } } |
總結(jié)
以上就是本文關(guān)于java內(nèi)部測試類代碼詳解的全部內(nèi)容,希望對大家有所幫助。感興趣的朋友可以繼續(xù)參閱本站其他相關(guān)專題,如有不足之處,歡迎留言指出。感謝朋友們對本站的支持!
原文鏈接:http://blog.csdn.net/wanghuiwei888/article/details/78797620