目录
一、内部类定义
二、实例内部类
?(1)实例化内部类对象
?(2)在内部类中定义静态成员变量
?(3)成员变量重名问题
(4)注意事项
三、静态内部类?
(1)实例化静态内部类对象
(2)在静态内部类中访问外部类的成员
四、匿名内部类
一、内部类定义
一个类的内部,定义的类叫做内部类
1.实例内部类
2.静态内部类
3.匿名内部类
二、实例内部类
就是在外部类的内部在写一个类
这个例子的外部类是OuterClass,内部类是InnerClass
class OuterClass{
public int data1 = 10;
private int data2 = 20;
public static int data3 = 30;
class InnerClass{ //实例内部类
public int data4 = 40;
private int data5 = 50;
public InnerClass(){
System.out.println("InnerClass的构造方法!");
}
public void method(){
System.out.println("InnerClass的一个普通方法!");
}
}
}
?(1)实例化内部类对象
外部类名.内部类 变量 = 外部类对象的引用
public class TestDemo {
public static void main(String[] args) {
OuterClass outerClass = new OuterClass();//需要先实例化外部类对象
OuterClass.InnerClass innerClass = outerClass.new InnerClass();
//或者一步到位
OuterClass.InnerClass innerClass1 = new OuterClass().new InnerClass();
}
}
?(2)在内部类中定义静态成员变量
实例内部类中不能定义静态的成员变量,但要定义 必须是编译的时候确定的值? ?(必须是static final的)因为加上final以后变成常量了 ,意味着编译的时候就确定这个值是几了
内部类中不能定义静态的成员方法,加上final也不行,final只能加在成员变量上
?(3)成员变量重名问题
<1>情况1:在实例内部类中,打印与外部类重名的成员变量
优先使用自己的(即内部类的)
class OuterClass{
public int data1 = 10;
class InnerClass{ //实例内部类
public int data1 = 40;
public void method(){
System.out.println(data1);
}
}
}
public class TestDemo {
public static void main(String[] args) {
OuterClass outerClass = new OuterClass();
OuterClass.InnerClass innerClass = outerClass.new InnerClass();
innerClass.method();//结果为40
}
}
?那如何拿到外部类的呢??
?<2>情况二:当在外部类中,打印与内部类重名的成员变量
优先使用自己的(即外部类的)
class OuterClass{
public int data1 = 10;
class InnerClass{ //实例内部类
public int data1 = 40;
public void method(){
System.out.println("这是内部类的方法!!");
System.out.println(OuterClass.this.data1);
}
}
public void outMethod(){
System.out.println("这是外部类的方法!!");
System.out.println(data1);
}
}
public class TestDemo {
public static void main(String[] args) {
OuterClass outerClass = new OuterClass();
outerClass.outMethod();//调用外部类的方法
}
}
?那如何拿到内部类的呢??
(4)注意事项
1.外部类中的任何成员都可以被在普通内部类方法中直接访问
2. 普通内部类所处的位置与外部类成员位置相同,因此也受public、private等访问限定符的约束,比如:public InnerClass,private IneerClass
而外部类的修饰限定符只有两个:public和什么都不加
3.在内部类方法中访问同名的成员时,优先访问自己的,如果要访问外部类同名的成员,必须:外部类名称.this.同名成员来访问
4.普通内部类对象必须在先有外部类对象前提下才能创建
5.普通内部类的非静态方法中包含了一个指向外部类对象的引用
6.外部类中,不能直接访问内部类中的成员,如果要访问必须先要创建内部类的对象。
三、静态内部类?
这个例子中外部类是OuterClass,静态内部类是InnerClass
class OuterClass{
public int data1 = 10;
private int data2 = 20;
public static int data3 = 30;
public void outMethod(){
System.out.println("这是外部类的方法!!");
}
static class InnerClass{ //静态内部类
public int data4 = 40;
private int data5 = 50;
public static int data6 = 60;
public void innerMethod(){
System.out.println("这是静态内部类的方法!!");
}
}
}
(1)实例化静态内部类对象
把静态内部类当作静态成员,静态成员不依赖于对象,所以我们要实例化静态内部类对象不需要外部类对象
类名.静态内部类? ?这里的类名是OuterClass
public class TestDemo {
public static void main(String[] args) {
OuterClass.InnerClass innerClass = new OuterClass.InnerClass();
//这里的OuterClass后面没有加(),不是实例化外部对象,是类名的意思
}
}
(2)在静态内部类中访问外部类的成员
在静态内部类类中,只能访问外部类静态的成员
那么我们如何访问非静态的成员呢??
需要外部类对象来调用它
方法一:
class OuterClass{
public int data1 = 10;
private int data2 = 20;
public static int data3 = 30;
static class InnerClass{
OuterClass outer1 = new OuterClass();//此时相当于一个成员变量
public void innerMethod(){
System.out.println("这是静态内部类的方法!!");
System.out.println(outer1.data1);
System.out.println(outer1.data2);
}
}
}
public class TestDemo {
public static void main(String[] args) {
OuterClass.InnerClass innerClass = new OuterClass.InnerClass();
innerClass.innerMethod();
}
}
方法二:写一个构造方法
class OuterClass{
public int data1 = 10;
private int data2 = 20;
public static int data3 = 30;
static class InnerClass{
OuterClass outer;
InnerClass(OuterClass outer){
this.outer = outer;
}
public void innerMethod(){
System.out.println(outer.data1);
System.out.println(outer.data2);
}
}
}
public class TestDemo {
public static void main(String[] args) {
OuterClass.InnerClass innerClass = new OuterClass.InnerClass(new OuterClass());
innerClass.innerMethod();
}
}
四、匿名内部类
匿名内部类不需要详细掌握,掌握以下几点即可
(1)访问匿名内部类的成员变量
(2)调用匿名内部类的方法
(3)定义其他方法
(4)重写匿名内部类的方法
class Test{
public int a;
public void test(){
System.out.println("test()!");
}
}
public class TestDemo {
public static void main(String[] args) {
new Test(){
}.a = 10;//访问a
new Test(){
}.test();//调用test()方法
new Test(){
public void test1(){
System.out.println("hi");//定义其他方法
}
}.test1();
new Test(){
@Override
public void test(){ //重写test()方法
System.out.println("哈哈哈");
}
}.test();
}
}
|