目录
Lambda表达式实例
需求:启动一个线程,在控制台输出一句话:多线程程序启动了
代码示例:
方法一:
创建类MyRunnable实现Runnable接口,重写run方法
public class MyRunnable implements Runnable{
@Override
public void run(){
System.out.println("多线程程序启动了");
}
}
主程序中创建构造方法,创建一个新的线程并将对象传入再start即可
MyRunnable my = new MyRunnable();
Thread t = new Thread(my);
t.start();
方法二:
使用匿名内部类方法
new Thread (new Runnable(){
@Override
public void run(){
System.out.println("多线程程序启动了");
}
}).start();
方法三:
使用Lambda表达式
new Thread( () ->{
System.out.print("多线程程序启动了");
}).start();
Lambda表达式的标准格式
格式:
- (形式参数)-> {代码块}
形式参数:如果有多个参数,参数之间用逗号隔开;如果没有参数,留空即可 - ->:由英文中画线和大于符号组成,固定写法。代表指向动作,也可以说是接下来要做的动作
- 代码块:是我们具体要做的事情,也就是平时写方法中的内容
Lambda实例1:(方法使用前提:1.有一个接口 2.接口中有且仅有一个抽象方法)
Eatable是一个接口EatableImpl是实现了Eatable接口的一个实现类
Eatable e = new EatableImpl();
useEatable(e);
useEatable(new Eatable(){
@Override
public void eat(){
System.out.println("55555555555");
}
});
用Lambda表达式写:
useEatable( () -> {
System.out.println("66666666666");
});
Lambda表达式实例2:(调用带参数的Lambda方法)
定义一个接口
public interface Flyable{
void fly(String s);
}
public static void main(String[] args){
useFlyable(new Flyable(){
@Override
public void fly(String s){
System.out.println(s);
System.out.println("123456");
}
});
useFlyable( (String s) -> { //带参数的抽象方法只需要在()中写上形参即可
System.out.println(s);
System.out.println("67890");
});
}
private static void useFlyable(Flyable f){
f.fly("5555");
}
Lambda表达式实例:(调用带参数和返回值的Lambda表达式)
定义一个接口
public interface Addable{
int add(int x,int y);
}
public static void main(String[] args){
Addablea((int x,int y)->{
//int sum = x+y;
//System.out.println(sum);
//当接口中的抽象方法有返回值时Lambda表达式必须有return值否则报错
return x+y;
});
}
private static void Addablea(Addable a){
int sum = a.add(1,4);
System.out.println(sum);
}
Lambda表达式的省略模式
-
//有多个形参时不能只省略一个
useAddable((x,int y) -> {
return x+y;
}); -
//如果参数有且仅有一个,那么小括号可以省略
useFlyable( s -> {
System.out.print(s);
}); -
//如果代码块的语句只有一条,可以省略大括号和分号
useFlyable( s -> System.out.print(s) ); -
//如果代码块的语句只有一条,可以省略大括号和分号,如果有return ,return也要省略掉
useFlyable( (x,y) -> x+y );
Lambda表达式的注意事项
注意事项:
- 使用Lambda必须要有接口,并且要求接口中有且仅有一种抽象方法
- 必须有上下文环境,编译器才能推到出Lambda对应的接口
根据局部变量的赋值得知Lambda对应的接口:Runnable r = () -> System.out.print(“Lambda表达式”);
根据调用方法的参数得知Lambda对应的接口:new Thread( () -> System.out.print(“Lambda表达式”) ).start();
Lambda表达式和匿名内部类的区别
所需类型不同
- 匿名内部类:可以是接口,也可以是抽象类,还可以是具体类
- Lambda表达式:只能是接口
使用限制不同
- 如果接口中有且仅有一个抽象方法,可以使用Lambda表达式,也可以使用匿名内部类
- 如果接口中多于一个抽象方法,则只能使用匿名内部类,而不能使用Lambda表达式
实现原理不同
- 匿名内部类:在编译后,会生成一个单独的class字节码文件
- Lambda表达式:在编译后没有一个单独的class字节码文件,对用的字节码会在运行的适合动态生成