一、匿名内部类
匿名内部类是一种没有名称的类,多用于只使用一次的情况,本质上就是其所继承的父类或接口的一个子类。
(一)继承普通类的情况
public class Test{
public void method()
{
System.out.println("通用方法");
}
public static void main(String[] args)
{
Test ts1=new Test();
ts1.method(); //调用普通方法
//创建内部类,等价于Test的一个子类,同时将其实例化为ts2
Test ts2=new Test()
{
public void method()
{
System.out.println("内部类方法");
}
};
ts2.method(); //调用内部类方法
}
}
(二)继承抽象类的情况
public abstract class Test{
public abstract void method(String a);
}
public class TT{
public static void main(String[] args)
{
Test ts=new Test()
{
public void method(String a)
{
System.out.println(a);
}
};
ts.method();
}
}
本案例中,ts 本质上就是抽象类 Test 的一个子类的实例化对象,在匿名内部类中对抽象类 Test 中的 method 方法进行重写,然后调用。
(三)继承接口的情况
public interface Test{
public void method(int a,int b);
}
public class TT{
public static void main(String[] args)
{
Test ts=new Test()
{
public void method(int a,int b)
{
System.out.println(a+b);
}
};
ts.method();
}
}
继承接口的情况与继承抽象类的情况类似,ts 仍然相当于接口 Test 的一个子类的实例化对象,重写方法后,用这个子类的实例化对象 ts 去调用这个子类的方法 method。
二、Lambda表达式
在很多情况下,匿名内部类的书写过于繁琐,此时可以用 Lambda 表达式代替,其语法格式为:()->{}。对应上述三种情况,代码更改如下:
(一)继承普通类的情况
public class Test{
public void method()
{
System.out.println("通用方法");
}
public static void main(String[] args)
{
Test ts1=new Test();
ts1.method(); //调用普通方法
//创建内部类,等价于Test的一个子类,同时将其实例化为ts2
Test ts2=()->{System.out.println("内部类方法");};
ts2.method(); //调用内部类方法
}
}
(二)继承抽象类的情况
public abstract class Test{
public abstract void method(String a);
}
public class TT{
public static void main(String[] args)
{
Test ts=(String a)->{System.out.println(a);};
ts.method();
}
}
(三)继承接口的情况
public interface Test{
public void method(int a,int b);
}
public class TT{
public static void main(String[] args)
{
Test ts=(int a,int b)->{System.out.println(a+b);};
ts.method();
}
}
三、精简 Lambda 表达式
① 参数类型可以省略
② 如果只有一个参数,() 可以省略
③ 如果方法体只有一条语句,{} 可以省略
④ 如果方法体中唯一的一条语句是 return 语句,省略 {} 的同时,return 关键字也要省略
对应上述三种情况,代码可进一步优化为:
Test ts2=()->System.out.println("内部类方法");
Test ts=a->System.out.println(a);
Test ts=(a,b)->System.out.println(a+b);