内部类使用及注意事项

什么叫内部类呢?

简单来说将一个类定义到另一个类里面,里面那个类就称为是内部类

内部类的访问特点:

内部类可以直接访问外部类中的成员,包括私有成员。外部类要访问内部类中的成员必须要建立内部类的对象才能访问。

内部类的用处:

内部类一般用于类的设计。分析事物时,发现该事物描述中还有事物,而且这个事物还在访问被描述事物的内容。这个时候,这个事物中的事物就定义成内部类来描述。

内部类的修饰符:

由于内部类被定义在成员位置,所以内部类可以被成员修饰符修饰。

内部类可以在其他类中直接访问,例:

class Outer{
        private int num=3;
        class Inner{
            void show(){
                System.out.println("show run"+num);
            }
        }
        public void method(){
            Inner in = new Inner();
            in.show();
        }
    }

    class InnerDemo{
        public static void main(String[]args){
            //直接访问外部类中的内部类中的成员。
            Outer.Inner in =new Outer().new Inner();
            in.show();
        }   
    }

如果内部类是静态的,其实相当于一个外部类。可以直接用外部类的对象调用内部类类名使用,例:

class Outer{
        private static int num=3;
        static class Inner{
            void show(){
                System.out.println("show run"+num);
            }
        }
        public static void method(){
            Inner in = new Inner();
            in.show();
        }
    }

    class InnerDemo{
        public static void main(String[]args){
            Outer.Inner in =new Outer.Inner();
            in.show();
        }   
    }

如果内部类中定义了静态的成员,该内部类也必须定义成静态的否则会编译失败,例:

class Outer{
        private static int num=3;
         class Inner{
            void show(){
                System.out.println("show run"+num);
            }
            public static void function(){
                System.out.println("function 运行了");
            }
        }
        public static void method(){
            Inner in = new Inner();
            in.show();
        }
    }

    class InnerDemo{
        public static void main(String[]args){
            Outer.Inner.function();
        }   
    }

结果为:
Compiling InnerDemo.java……
InnerDemo.java:63: 错误: 内部类Outer.Inner中的静态声明非法
public static void function(){
^
修饰符 ‘static’ 仅允许在常量变量声明中使用
InnerDemo.java:68: 错误: 无法从静态上下文中引用非静态 变量 this
Inner in = new Inner();
^
2 个错误
[Finished in 0.6s]

为什么内部类可以直接访问外部类的成员:

因为内部类被定义在外部类的成员位置,该内部类就持有了外部类的引用(外部类名.this)

内部类可以放在局部位置上 ,例:

public class InnerDemo2{
    public static void main(String[]args){
        new Outer().method();
    }
}
class Outer{
    int num=3;
    void method(){
        class Inner{
            void show(){
                System.out.println("show......"+num);
            }
        }
        Inner in = new Inner();
        in.show();
    }
}

当内部类处于局部位置时,该内部类只能访问局部中被final修饰的局部变量。

public class InnerDemo2{
    public static void main(String[]args){
        Outer out = new Outer();
        Object obj = out.method();
    }
}
class Outer{
    final int num=3;
    Object method(){
        int x = 9;
        class Inner{
            void show(){
                System.out.println("show......"+x);
            }
        }
        Object in = new Inner();
        // in.show();
        return in;
    }
}   

匿名内部类:

匿名内部类其实就是内部类的简写格式,是一个匿名 的子类对象,可以直接在类的结束部分加点调用。
简写的前提:内部类必须实现或者继承一个外部类或者接口

public class InnerDemo3{
    public static void main(String []args){
        new Outer().method();
    }
}

abstract class Demo{
    abstract void show();
}

class Outer{
    int num=4;
    public void method(){
        new Demo(){
            void show(){
                System.out.println("show......"+num);
            }
        }.show();
    }
}

匿名内部类的使用场景:

当函数参数是接口类型时,且接口中的方法不超过三个,这个时候就可以用匿名内部类作为实际参数进行传递。

使用匿名内部类的注意事项:

当在创建内部类对象的时候可以调用子类特有的方法,当创建对象的父类引用类型时,就不能引用子类特有的方法了,因为对象已经向上进行了转型。
例:1.在创建时调用

public class InnerDemo5{
    public static void main(String[]args){
        new Outer().method();
    }
}

class Outer{
    void method(){
        new Object(){
            public void show(){
                System.out.println("show run");
            }
        }.show();
    }
}

结果如下:

Compiling InnerDemo5.java……
——Output——
show run
[Finished in 0.6s]
2.创建子类对象的父类引用类型时,调用子类特有的方法

public class InnerDemo5{
    public static void main(String[]args){
        new Outer().method();
    }
}

class Outer{
    void method(){
        Object obj = new Object(){
            public void show(){
                System.out.println("show run");
            }
        };
        obj.show();
    }
}

运行结果如下:

Compiling InnerDemo5.java……
InnerDemo5.java:14: 错误: 找不到符号
obj.show();
^
符号: 方法 show()
位置: 类型为Object的变量 obj
1 个错误
——Output——
[Finished in 0.6s]

猜你喜欢

转载自blog.csdn.net/ILYPTING/article/details/71272598
今日推荐