java内部类及类的加载顺序(二)
上篇博文我已将介绍过了类的加载顺序了,今天正式回归到内部类的主题上来,介绍一下四大内部类,内部类的作用:
- 内部类方法可以访问该类定义所在作用域中的数据,包括private的数据
- 内部类可以对同一个包中的其他类隐藏起来
一、静态内部类
定义在类内部的静态类,就是静态内部类
public class Out {
public static int i=0;
private int j;
//静态内部类--Inner
public static class Inner{
public void print() {
System.out.println("i="+i);
}
}
}
- 1.可以访问外部类所有的静态变量和方法,即使是 private 的也一样。
- 2.静态内部类和一般类一致,也可以定义静态变量、方法,构造方法等。
- 3.其他类使用静态内部类要使用“外部类.静态内部类”的方式,例如:Out.Inner inner=new Inner(); 而在本类可以不需要这么写
- Java集合类HashMap内部就有一个静态内部类Entry
二、成员内部类
定义在类内部的非静态类,就是成员内部类。
public class Out {
private static int i=0;
private int j;
//成员内部类--Inner(没有static关键字)
public class Inner {
public void print() {
System.out.println("i="+i);
System.out.println("j="+j);
}
}
//直接访问模式
public static void main(String[] args) {
Out.Inner inner=new Out().new Inner();
}
}
三、局部内部类
- 定义在方法中的类就是局部内部类,如果一个类只在某个方法中使用,则可以考虑使用局部类
- 注意:
- 1.局部内部类不能用public或private访问修饰符进行声明,因为它的作用域被限定在这个方法中了,即已经对外部世界完全隐藏起来了
- 2.局部内部类不但可以访问包含它们的外部类,而且可以访问局部变量,但是局部变量是final修饰的
public class Out {
private static int i;
private int j;
public void test(final int c) {
final int d = 1;
//局部内部类
class Inner {
public void print() {
System.out.println(c);
}
}
}
}
四、匿名内部类(属于局部内部类)
匿名内部类我们必须要继承一个父类或者实现一个接口,当然也仅能只继承一个父类或者实现一个接口。同时它也是没有class关键字,这是因为匿名内部类是直接使用new来生成一个对象的引用。
//抽象类
abstract class Bird {
private String name;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public abstract int fly();
}
public class Test {
public void test(Bird bird){
System.out.println(bird.getName() + "能够飞 " + bird.fly() + "米");
}
public static void main(String[] args) {
Test test = new Test();
//匿名内部类
test.test(new Bird() {
public int fly() {
return 10000;
}
public String getName() {
return "大雁";
}
});
}
}
匿名内部类也是我们平时经常用到的,比如在java的GUI中,经常要为某个控件添加一个事件,就用的是匿名内部类;当想要定义一个回调函数且不想编写大量代码的时候,使用匿名内部类是比较便捷的
使用内部类注意事项
- 1.内部类中所以的静态变量必须声明为final,原因:一个静态域只有一个实例,不过对于每个外部类对象,会分别有一个单独的内部类实例;如果这个静态域不是final,它就可能不是唯一的
- 2.内部类不能有static方法