最近學到的Lambda表達式基礎知識
前言
只有光頭才能變強。
中秋去了躺上海,在外灘上打了個卡:
外灘緊接著學了一下Java的函數式編程,給大家整理了一下,一起學習!
一、Lambda用法
之前寫Optional這個類的時候,簡單說了一下Lambda是怎么用的,這里再跟大家一起回顧一下,Lambda的語法是這樣的:
語法以Lambda語法創(chuàng)建線程和匿名內部類創(chuàng)建線程的區(qū)別(顯然代碼少了很多!):
public?static?void?main(String[]?args)?{
????//?用匿名內部類的方式來創(chuàng)建線程
????new?Thread(new?Runnable()?{
????????@Override
????????public?void?run()?{
????????????System.out.println("公眾號:Java3y---關注我!");
????????}
????});
????//?使用Lambda來創(chuàng)建線程
????new?Thread(()?->?System.out.println("公眾號:Java3y---關注我!"));
}
使用Lambda表達式,實際就是創(chuàng)建出該接口的實例對象。
返回一個Runnable對象實例圖示;Runnable接口來舉例:
以Runnable接口為例使用Labmda表達式需要函數式編程接口,比如在Runnable接口上我們可以看到@FunctionalInterface注解(標記著這個接口只有一個抽象方法)
函數式編程接口只有一個抽象方法1.1 函數式編程接口
從上面的代碼例子可以看出,我們使用Lambda表達式創(chuàng)建線程的時候,并不關心接口名,方法名,參數名。我們只關注他的參數類型,參數個數,返回值。
JDK原生就給我們提供了一些函數式編程接口方便我們去使用,下面是一些常用的接口:
常用的函數式編程接口簡單說明一下:
表格中的一元接口表示只有一個入參,二元接口表示有兩個入參
以BiFunction為例
常用的函數式接口Demo:
//?Consumer?一個入參,無返回值
Consumer?consumer?=?s->?System.out.println(s);
consumer.accept("Java3y");
//?Supplier?無入參,有返回值
Supplier?supplier?=?()?->?"Java4y";
String?s?=?supplier.get();
System.out.println(s);
//.....
使用Lambda時,要記住的就兩點:
Lambda返回的是接口的實例對象
有沒有參數、參數有多少個、需不需要有返回值、返回值的類型是什么---->選擇自己合適的函數式接口
1.2 方法引用
在學Lambda的時候,還可能會發(fā)現(xiàn)一種比較奇怪的寫法,例如下面的代碼:
//?方法引用寫法
Consumer?consumer?=?System.out::println;
consumer.accept("Java3y");
如果按正常Lambda的寫法可能是這樣的:
//?普通的Lambda寫法
Consumer?consumer?=?s?->?System.out.println(s);
consumer.accept("Java3y");
顯然使用方法引用比普通的Lambda表達式又簡潔了一些。
如果函數式接口的實現(xiàn)恰好可以通過調用一個方法來實現(xiàn),那么我們可以使用方法引用
函數式接口的實現(xiàn)恰好可以通過調用一個方法來實現(xiàn)方法引用又分了幾種:
靜態(tài)方法的方法引用
非靜態(tài)方法的方法引用
構造函數的方法引用
方法引用Demo:
public?class?Demo?{
????public?static?void?main(String[]?args)?{
????????//?靜態(tài)方法引用--通過類名調用
????????Consumer?consumerStatic?=?Java3y::MyNameStatic;
????????consumerStatic.accept("3y---static");
????????//實例方法引用--通過實例調用
????????Java3y?java3y?=?new?Java3y();
????????Consumer?consumer?=?java3y::myName;
????????consumer.accept("3y---instance");
????????//?構造方法方法引用--無參數
????????Supplier?supplier?=?Java3y::new;
????????System.out.println(supplier.get());
????}
}
class?Java3y?{
????//?靜態(tài)方法
????public?static?void?MyNameStatic(String?name)?{
????????System.out.println(name);
????}
????//?實例方法
????public?void?myName(String?name)?{
????????System.out.println(name);
????}
????//?無參構造方法
????public?Java3y()?{
????}
}
結果如下:
結果最后
Lambda雖然代碼看起來是簡潔,但是如果復雜的話還是比較難看明白的。
在學習Lambda的時候,首先我們得知道有哪些常用函數式編程接口,這些函數式編程接口的有什么區(qū)別(參數個數、返回值類型)
Lambda表達式返回的是接口對象實例,如果函數式接口的實現(xiàn)恰好可以通過調用一個方法來實現(xiàn),那么我們可以使用方法引用來替代Lambda表達式
最后再完整舉個例子:
//?Supplier是一個無入參帶返回的值的函數式編程接口
//?()?-> new Java3y()這整句Lambda表達式,返回的是Supplier接口的實例。從Lambda表達式可以看出無參數,帶返回值
Supplier?supplier?=?()?->?new?Java3y();?
//?由于這個“()?->?new?Java3y()”Lambda表達式可以通過調用一個方法就實現(xiàn)了,那么我們可以優(yōu)化成方法引用
Supplier?supplier2?=?Java3y::new; 推薦閱讀:
喜歡我可以給我設為星標哦

好文章,我?在看?

