Java内部类
·内部类
概念:
·内部类:将一个类定义在另一个的里面,这个类就叫内部类。外面的类叫外部类。内部类跟类里面的方法,构造器等地位相同,都属于外部那个类的成员。
特点:
·内部类能访问外部类的私有数据。就跟本类的方法中调用本类中的私有属性是一样的,因为内部类也是外部类的成员他们是一体的所以自己能访问自己的数据。
·外部也能访问内部类的数据,但是外部类不能直接访问内部类中的数据,需要在外部类创建内部类的对象,通过这个对象来调用内部类的数据。
·其他类中也能访问外部类的内部类。
·内部类还能被继承,继承的子类是一个普通的类,也可能是一个内部类。
·内部类这个成员可以放在外部类中定义,它就是类的成员了;但是也可以放在外部类的方法中定义,放在方法中的内部类叫“局部内部类”,此时这个局部内部类就不是类的成员。
·匿名内部类和局部内部类不是类的成员。
·内部类是类的成员所以可以使用访问控制修饰符和static来修饰,使用static修饰的内部类是静态内部类,没有使用static修饰的内部类是“非静态内部类”。
·内部类编译完后名字是外部类名字@内部类名字.class
·内部类访问外部类属性使用“外部类名.this.外部类属性”
·静态成员不能访问非静态成员,所以外部静态方法静态代码块不能访问非静态内部类。
·Java语法规定不能在非静态内部类中定义静态成员。可以在静态类中定义静态成员。
·静态成员不能访问非静态成员,所以在内部类中不能访问外部类对象成员,只能访问外部类的类成员。
·可以在接口中定义静态内部类,因为接口中的默认修饰符是public static,所以定义的内部类就是静态内部类。
·静态成员不能访问非静态成员,但是非静态成员可以访问静态成员。静态内部类的成员只能访问外部类的类成员,不能访问外部类的对象成员。
·内部类可以直接访问外部类的私有属性,外部类可以通过内部类对象访问内部类的私有属性。
·非静态内部类的对象存在外部类的对象中。
·静态内部类的对象存在外部类中。
·在其他类中创建外部类的内部类的对象: 外部类.内部类 变量名 = 外部类对象.new内部类构造器();
·在其他类中创建外部类的静态内部类对象:外部类.内部类变量名 = new 外部类名字.内部类构造器();
·总之调用内部类就要写绝对路径。
·匿名内部类:
现在我告诉你创建对象的方法不止有构造器,匿名类也能创建对象!创建匿名类时会创建一个该类的对象,执行完类体后类消失,匿名内部类不能重复使用。
·匿名内部类不能是抽象类
·匿名内部类不能定义构造器
·匿名内部类能访问外部类final修饰的局部变量。
·匿名内部类实现接口的抽象方法跟普通类一样,需要实现接口中的全部的抽象方法。
·匿名内部类 new 接口() { }创建接口的对象,因为匿名内部类也不能创建构造器,所以这里不能传入参数。就是一个默认构造器一样的。
创建匿名内部类语法:
new 父类构造器(实参列表) | 实现接口(){
类体
}
使用场景:
·不让同一个包中的类访问这个类,就可以把这个类定义在其他类的内部。
·匿名内部类创建某个接口的对象。
例子:匿名内部类
interface Product { public double getMoney(); public String getName(); } public class AnonymousTest { public void test(Product p) //使用匿名内部类创建对象。 { System.out.println(p.getMoney()); System.out.println(p.getName()); } public static void main(String[] args) { AnonymousTest a = new AnonymousTest(); a.test(new Product() { //给方法传递一个匿名内部类,它会创建一个对象。重写接口的2个抽象方法。调用test方法传入Product对象。 public double getMoney(){ return 799; } public String getName(){ return "msi r7750"; } }); } }
例子:内部类实现抽象类方法
abstract class Device { private String name; public abstract double getPrice(); public Device(){}; public Device(String name) { this.name = name; } public String getName() { return this.name; } } public class AnonInner { public void test(Device d) //这个地方一看就是传入一个对象 { System.out.println( d.getName() + " " + d.getPrice()); } public static void main(String[] args) { AnonInner a = new AnonInner(); //传入方法的参数是匿名内部类,实现了抽象类的方法 a.test(new Device("R7750") { //匿名内部类传了一个R7750参数给Device()构造器初始化属性 public double getPrice() { return 799.0; } }); //匿名内部类 Device d = new Device() { public double getPrice() { return 1; } public String getName() { return "abc"; } }; a.test(d); } }