726
阿裏雲
技術社區[雲棲]
一個Java 8中簡單Lambda表達式程序
我嚐試過把Lambda表達式融入到我的代碼中,下麵的代碼例子是此次嚐試的結果。對於那些完全不知道Lambda表達式的Java程序員,我強烈建議在繼續閱讀之前,瀏覽一下這篇文章。
Ok,現在你已經熟悉Lambda表達式了(在閱讀過推薦的Lambda入門文章之後),那我們現在開始學習一個我認為很好的Lambda表達式的例子。
考慮一下這種場景:某些操作在執行之前需要做預處理,執行之後需要做後期處理。待執行的操作會隨著行為的不同而變化。預處理會提取出這個操作所需的必要參數,後期處理做一些清理的工作。
我們來看看如何利用接口與接口的匿名實現類模擬這個場景。
使用匿名內部類
一個提供了必要行為方法的接口實現:
1 |
interface OldPerformer {
|
3 |
public void performTask(String id, int status);
|
接下來是一些預處理和後期處理方法:
01 |
public class PrePostDemo {
|
03 |
static void performTask(String id, OldPerformer performer) {
|
05 |
System.out.println( "Pre-Processing..." );
|
07 |
System.out.println( "Fetching the status for id: " + id);
|
11 |
//Some status value fetched
|
13 |
performer.performTask(id, status);
|
15 |
System.out.println( "Post-processing..." );
|
我們需要傳遞2樣東西:預處理所需的標識,以及操作的實現。如下所示:
01 |
public class PrePostDemo {
|
03 |
public static void main(String[] args) {
|
05 |
//has to be declared final to be accessed within
|
07 |
//the anonymous inner class.
|
09 |
final String outsideOfImpl = "Common Value" ;
|
11 |
performTask( "1234" , new OldPerformer() {
|
15 |
public void performTask(String id, int status) {
|
17 |
System.out.println( "Finding data based on id..."
|
21 |
System.out.println(outsideOfImpl);
|
23 |
System.out.println( "Asserting that the status matches" );
|
29 |
performTask( "4567" , new OldPerformer() {
|
33 |
public void performTask(String id, int status) {
|
35 |
System.out.println( "Finding data based on id..." );
|
37 |
System.out.println(outsideOfImpl);
|
39 |
System.out.println( "Update status of the data found" );
|
從上麵的代碼可以看出,匿名內部類外部的變量要想被匿名內部類訪問,需要聲明成final。例子的代碼輸出如下:
01 |
Pre-Processing...</pre> |
02 |
Fetching the status for id: 1234
|
04 |
Finding data based on id... |
08 |
Asserting that the status matches |
14 |
Fetching the status for id: 4567
|
16 |
Finding data based on id... |
20 |
Update the status of the data found |
使用Lambda表達式
我們來看看如何用Lambda表達式實現上述例子:
01 |
public class PrePostLambdaDemo {
|
03 |
public static void main(String[] args) {
|
05 |
//Need not be declared as final for use within a
|
07 |
//lambda expression, but has to be eventually final.
|
09 |
String outsideOfImpl = "Common Value" ;
|
11 |
doSomeProcessing( "123" , (String id, int status) -> {
|
13 |
System.out.println( "Finding some data based on" +id);
|
15 |
System.out.println(outsideOfImpl);
|
17 |
System.out.println( "Assert that the status is " +status );
|
21 |
doSomeProcessing( "456" , (String id, int status) -> {
|
23 |
System.out.print( "Finding data based on id: " +id);
|
25 |
System.out.println(outsideOfImpl);
|
27 |
System.out.println( "And updating the status: " +status);
|
33 |
static void doSomeProcessing(String id, Performer performer ){
|
35 |
System.out.println( "Pre-Processing..." );
|
37 |
System.out.println( "Finding status for given id: " +id);
|
41 |
performer.performTask(id, status);
|
43 |
System.out.println( "Post-processing..." );
|
51 |
public void performTask(String id, int status);
|
除了有趣的Lambda表達式語法之外,還有一點不同,那就是Lambda表達式外部的變量沒有聲明成final。但最終變量還是會成為常量,這意味著outsideOfImpl 在聲明及初始化之後的值不能被更改。
這個例子隻是展示了如何使用清晰明了的Lambda表達式代替匿名內部類。
一個小提示:JDK8的發布時間推遲到了2014年2月,完整的發布時間表可以從這裏查閱。我每天都會更新Lambda的構建項目,如果在最新的構建中出現了任何問題,請隨時聯係我。我會盡最大努力持續構建,並且會在這裏發表最新的例子。
另一個提示:不要讓Java 8的更新使你不知所措,大部分新特性已經存在於其他編程語言中。我發現學習Lambda表達式的語法和方法可以幫助我以函數式的思維進行思考,對此我還應特別感謝Scala閉包。
最後更新:2017-05-23 10:02:15