java8之lambda表达式
前言
话说java 8的最大变化就是引入了Lambda表达式,Lambda表达式使代码显得更加的紧凑,同时,它也是一种传递行为的编程方式。
编程示例
我觉得还是不多说了,最好的方式就是例子,大家的模仿能力都是很强的,看例子一看就懂。
public static void main(String[] args) {
new Thread(()-> System.out.println("hello lambda!")).start();
}
输出结果:
hello lambda!
main函数中的这一行代码是什么供能呢?没错,它就是一个线程,打印“hello lambda!”,有没有被它的简单吓到。或许你会觉得这难以理解,我们的Runnable哪去了?如果我们要实现更多打印,怎么实现呢?一大堆问题,我们一个一个解决。首选,我们看看要打印多行怎么实现。
public static void main(String[] args) {
new Thread(()-> {
System.out.println("hello lambda!");
System.out.println(Thread.currentThread().getName());
}).start();
}
输出结果:
hello lambda!
Thread-0
哈哈,就是加一个“{}”而已。然后,我们来说第二个问题,Runnable去哪了,说这个问题之前,我们来回顾之前的简单线程是如何实现的。
public static void main(String[] args) {
new Thread(new Runnable(){
@Override
public void run() {
System.out.println("hello lambda!");
System.out.println(Thread.currentThread().getName());
}
}).start();
}
输出结果:
hello lambda!
Thread-0
如上所示,是我们常见的线程实现方式。尽管我们使用了匿名内部类,但是我们还是很清楚的知道实现了Runnable的run方法。可是在lambda表达式的实现里面呢,我们看不到Runnable的子类对象,看不到run方法。在前言中,有提到,lambda使我们的代码变得更加紧凑,所以能不要的就不要了。
在这个例子中,我们关心Runnable子类对象叫什么吗?我们需要关心run方法名字并再把它写一遍吗?这都不需要,我们只关心我们的任务是做什么,只关心我们要传递的的行为。
还有那“()”是什么意思?这个你就理解为是要实现的run方法的后面那个“()”吧,run方法是无参的,所以只剩下“()”,对于其他函数式接口中,可能就有参数了。
说到这,也许有点晕了,什么是函数接口?有参数的情况怎么来写呢?下面再慢慢道来。
函数接口
说到函数接口,最好的例子就是把Runnable接口看一看。
@FunctionalInterface
public interface Runnable {
/**
* When an object implementing interface <code>Runnable</code> is used
* to create a thread, starting the thread causes the object's
*......
*
* @see java.lang.Thread#run()
*/
public abstract void run();
}
函数接口就是只有一个抽象方法的接口。这也不难理解,我们在之前的例子中讲到,lambda是传递行为的,如果存在多个抽象方法,又没有方法名,那怎么知道要传递的是那个方法的行为呢?所以函数接口抽象方法只能有一个。
@FunctionalInterface注解又是什么意思呢?它就是函数接口的注解,告诉程序猿,该接口是函数接口,只能存在一个抽象方法,不要随意添加其他的抽象方法,否则编译报错!
当然,在java 8中是存在默认实现的,一个函数接口中是可以存在多个默认实现的。
自定义函数接口
@FunctionalInterface
interface Operator{
public abstract double operator(int x,int y);
}
public class Example03 {
public static void opera(Operator o,int x,int y){
System.out.println("输出结果:"+o.operator(x,y));
}
public static void main(String[] args) {
opera((a,b)->(a+b),1,2);
}
}
输出结果:
输出结果:3.0
这是一个很简单的示例,一个函数接口Operator,一个抽象方法operator,并有两个参数。在静态方法中,我们有三个参数,一个Operator和两个int型参数。在main方法中,我们调用了静待方法,很显然需要在接口函数处传入一个行为,即“(a,b)->(a+b)”,其中“(a,b)”可理解为operator(int a,int b),“(a+b)”就是要表达的行为,两数相加。后面的两个参数1、2,就是传入给“行为”的两个参数了。
到此,对lambda表达式是否有一个初步的认识了呢?关于这部分先讲到这,知识得慢慢吸收。