一、实例内部类
1. 语法规则
(1)在实例内部类中,不能定义一个静态的成员变量,如果非要定义,只能在修饰类型之前加 static final
(2)如何通过实例内部类实例化对象?
OutClass outClass = new OutClass();
OutClass.InnerClass innerClass = outClass.new InnerClass();
//外部类名. 内部类名 + 内部类的对象变量 = 外部类的对象变量. new 内部类( )
(3)在实例内部类中,如果包含了和外部类同名的成员变量,那么如何在实例内部类中进行访问?
实例内部类中,包含两个 this,一个是外部类 this,一个是自己内部类的 this
外部类名. this.(变量) -> 访问的是外部类的成员变量
this.(变量) -> 访问的是内部类的成员变量
2. 代码演示
程序清单1:
class OutClass{
public int a = 1;
public int b = 2;
public String str = "abc";
//实例内部类,你可以把它当作是外部类的一个普通实例的成员
class InnerClass{
public int a = 99;
public int b = 100;
private int c = 3;
public static final int d = 5;
//public static int d = 5; //error
public InnerClass(){
System.out.println("内部类不带参数的构造方法");
}
public void test(){
System.out.println(OutClass.this.a);
System.out.println(this.a);
System.out.println(OutClass.this.b);
System.out.println(b);
System.out.println(c);
}
}
}
public class Test1 {
public static void main(String[] args) {
OutClass outClass = new OutClass();
OutClass.InnerClass innerClass = outClass.new InnerClass();
innerClass.test();
}
}
输出结果:
二、静态内部类
只要和 static 相关的,都与类直接相关联,而与对象并无多大关系,以下对静态内部类的测试也是如此。我们可以发现静态内部类和外部类息息相关,不需要依赖外部类实例化的对象。因为实际上,外部类中的内部类和外部类中的成员在地位上是相等的,所以语法层面也是一样的。
1. 语法规则
- 如何通过静态内部类实例化对象?
OutClass2 outClass2 = new OutClass2();
OutClass2.InnerClass2 innerClass2 = new OutClass2.InnerClass2();
//外部类类名.内部类类名 + 内部类的对象变量 = new 外部类类名.内部类类名()
2. 代码演示
这里有些部分和实例内部类的使用语法是一样的,我只演示一些不同的地方。
程序清单2:
class OutClass2{
public int a = 1;
public int b = 2;
public String str = "abc";
static class InnerClass2{
public int a = 99;
public static final int d = 5;
public static int e = 5; //right
public InnerClass2(){
System.out.println("内部类不带参数的构造方法");
}
public void test(){
//System.out.println(str); //error
//正确访问外部内的成员
System.out.println(new OutClass2().str); //right
System.out.println(new OutClass2().a);
System.out.println(a);
}
}
}
public class Test2 {
public static void main(String[] args) {
OutClass2 outClass2 = new OutClass2();
OutClass2.InnerClass2 innerClass2 = new OutClass2.InnerClass2();
innerClass2.test();
}
}
输出结果:
三、匿名内部类
程序清单3:
/**
* 匿名内部类
*/
class Unnamed{
public void test(){
System.out.println("abc");
}
}
class Unnamed2{
public void test2(){
System.out.println("abc");
}
}
public class Test3 {
public static void main(String[] args) {
//匿名对象调用 test() 方法
new Unnamed(){
}.test();
new Unnamed2(){
@Override
public void test2() {
System.out.println("我们可以重写 test2() 方法");
}
}.test2();
}
}
输出结果: