- 内部类:可以将一个类的定义放在另一个类的定义内部,这就是内部类。
- 内部类是一个编译时概念,编译后外部类及其内部类会生成两个独立的class文件: OuterClass.class和OuterClass$InnerClass.class。
- 在Java中内部类主要分为四种:成员内部类、局部内部类、匿名内部类、静态内部类。
内部类的好处
《Thinking in Java》中有这样一句话:使用内部类最吸引人的原因是:每个内部类都能独立地继承一个(接口的)实现,所以无论外部类是否已经继承了某个(接口的)实现,对于内部类都是没有影响的。
(1)使用内部类最大的优点就是可以实现多重继承问题
Java中只能继承一个类,多重继承在没有内部类之前是使用接口来实现的。但使用接口有时候有很多不方便的地方。比如我们实现一个接口就必须实现它里面的所有方法。而有了内部类就不一样了,它可以使我们的类继承多个具体类或抽象类。
(2)可以解决同时 继承类和实现接口 的时候,类和接口中出现同名方法的情况
(3)内部类提供了更好的封装和隐藏,除了外部类,其他类都不能访问内部类。而且,一般外部类,是不允许有private和protected权限的,但是内部类可以。
(4)内部类中的属性和方法,即使是外部类也不能直接访问,相反,内部类拥有外部类所有元素的访问权限,可以直接访问外部类的属性和方法,即便是private。
(5)内部类可以有多个实例,每个实例都有自己的状态信息,并且与其他外部类对象的信息相互独立。
(6)在单个外部类中,可以让多个内部类以不同的方式实现同一个接口,或者继承同一个类,不受外部类是否继承接口影响。
(7)内部类并没有令人迷惑的“is-a”关系,它就是一个独立的实体。
(8)有利于回调函数的编写。
成员内部类
(1)成员内部类作为外部类的一个成员存在,与外部类的属性、方法并列,可以无限制的访问外部类的所有成员,即使是private的也可以访问。但是外部类要访问内部类的成员属性和方法则要通过内部类实例来访问。
(2)成员内部类不能存在任何static的静态变量和方法;
(3)成员内部类是依附于外部类的,所以只有先创建了外部类才能够创建内部类;
(4)用内部类定义在外部类中不可访问的属性,这样就在外部类中实现了比外部类的private还要小的访问权限。
public class OuterClass { private String str; public void outerDisplay(){ System.out.println("outerClass..."); } public class InnerClass{ public void innerDisplay(){ //使用外部类的属性 str = "chenssy..."; System.out.println(str); //使用外部类的方法 outerDisplay(); } } /*推荐使用getxxx()来获取成员内部类,尤其是该内部类的构造函数无参数时 */ public InnerClass getInnerClass(){ return new InnerClass(); } public static void main(String[] args) { OuterClass outer = new OuterClass(); OuterClass.InnerClass inner = outer.getInnerClass(); inner.innerDisplay(); } } -------------------- chenssy... outerClass...
局部内部类
(1)在方法中或者作用域中定义的内部类,局部内部类与成员内部类基本一致,只是它们的作用域不同,局部内部类只能在该方法中被使用,出了该方法就会失效。
(2)局部内部类的使用主要是解决比较复杂的问题,想创建一个类来辅助我们的解决方案,但又不希望这个类是公共可用的,所以就产生了局部内部类。
(3)与局部变量相似,在局部内部类前面不能使用private、protected、public等访问修饰说明符修饰,也不能使用static修饰,但可以使用final和abstract修饰。
(4)局部内部类中不可定义static静态变量,static方法中定义的内部类可以访问外部类定义的static成员。
(5)局部内部类可以访问外部类的局部变量(即方法内的变量),但是变量必须是final。
(6)在类外不可直接生成局部内部类(保证局部内部类对外是不可见的)。要想使用局部内部类时,需要生成对象,对象调用方法,在方法中才能调用局部内部类。
//定义在方法中: public class Parcel5 { public Destionation destionation(String str){ class PDestionation implements Destionation{ private String label; private PDestionation(String whereTo){ label = whereTo; } public String readLabel(){ return label; } } return new PDestionation(str); } public static void main(String[] args) { Parcel5 parcel5 = new Parcel5(); Destionation d = parcel5.destionation("chenssy"); } }
//定义在作用域中: public class Parcel6 { private void internalTracking(boolean b){ if(b){ class TrackingSlip{ private String id; TrackingSlip(String s) { id = s; } String getSlip(){ return id; } } TrackingSlip ts = new TrackingSlip("chenssy"); String string = ts.getSlip(); } } public void track(){ internalTracking(true); } public static void main(String[] args) { Parcel6 parcel6 = new Parcel6(); parcel6.track(); } }
静态内部类