Inner Classes
这个inner classes的作用
1. Hiding code
2. 可以知道它周围的class也就是在它外部的那个class,可以和它沟通。
3. 内部类可以不需要加任何说明就访问外部这个类的对象和方法,C++中这个类没有这个特性
4. 把接口的实现隐藏了,每次返回的都是实现接口的一个对象
5. 普通的class不能被private或者protected修饰,只有内部类可以,这样的话内部类只能被外围的类或者它的子类(protected时)访问。
6. 每个内部类都可以独立实现一个接口或者继承一个类,不用在意外部类是否有继承还是什么,这样的话使接口实现起来更加地灵活。而且inner class就相当于外部类实现了多个接口,继承了多个抽象类
7. 注意这个inner class不是 “is-a”的关系,它是独立的一个关系
创建inner classes对象
1. 在外部的类中写生成innerclass的方法,然后用OuterClassName.InnerClassName声明类
2. 这个类的对象不能是static的,因为它需要有reference to enclosing class的东西
当然如果是static inner class那就可以是static的
3. 还可以用
OuterClassName out=new OuterClassName();
OuterClassName.InnerClassName inner=out.new InnerClassName () 来创建对象
注意一定要通过外部类的对象.new来创建,而不是直接外部类.new来创建
4. 如果innner class是static那么创建这个对象可以是
OuterClassName.InnerClassName inner= new InnerClassName ()不能又用out.new了
Inner class内部书写
1. Inner class调用外部类的this,需要这么写OuterClassName.this
2. Inner class还可以写在方法中,可以写在任意位置(甚至在if语句中),之后只要返回这个类的引用就可以了
3. Inner class还可以是匿名类来实现接口
比如说一个接口名字是contents
那么你可以写一个方法
Public contents call(){
return new contents(){
private int i = 11;
public int value() { return i; }
};
}
- 当你使用一个匿名类的时候如果需要传参直接在匿名类中使用的,那么这个参数必须是final,不然的话可以是不加final
比如
public Destination destination(final String dest) {
return new Destination() {
private String label = dest;
public String readLabel() { return label; }
};
}
- 在匿名类中写构造函数直接写一个{}就可以了
比如
public Destination destination(final String dest, final float price) {
return new Destination() {
private int cost;
// Instance initialization for each object:
{
cost = Math.round(price);
if(cost > 100)
System.out.println("Over budget!");
}
这一块就是构造函数
private String label = dest;
public String readLabel() { return label; }
};
}
- 匿名类不能同时实现两个(继承类或者接口)因为它是匿名的,而且它的构造方法也只能有一种,不能重载。
Nested class
1. 如果一个inner class是static那么这个类就被称为nested class因为它没有和外部类有关联。
(1) 不需要外部对象来创内部类
(2) 不能从内部类访问外部类中的non-static变量和方法
- 可以在接口中定义嵌套类,这样就可以在接口中的嵌套类中实现接口
比如
public interface ClassInInterface {
void howdy();
class Test implements ClassInInterface {
public void howdy() {
System.out.println("Howdy!");
}
public static void main(String[] args) {
new Test().howdy();
}
}
} /* Output:
Howdy!
*///:~
- 如果是在嵌套类中定义main方法,那么会独立编译出一个OutsiderClassName$InnerClassName.class的单元,你为了减少编译后程序的大小你可以测试之后去掉这个程序。
Control framework
继承inner class - 可以继承内部类,但是语法稍稍有点不同
构造器默认的是不行的,需要自己写一个构造器
Inheritant(enclosingClassReference ecr)
{
ecr.super();
}
这样子才能很好地把enclosingClassReference 中的inner class的引用传给这个子类
2. 如果一个类继承了一个有内部类的类,如果它重新写了一个不一样的内部类,这个内部类不会被override,调用的时候还是父类的inner class,只有外部类extends外部类,内部类extends内部类,这样才能override。