lambda 基礎

1、lambda basic

粗暴點:<font color="#f12242">只包含一個方法的接口,能夠稱爲函數接口(那麼就可使用lambda表達式)</font>.例以下圖:

/** 字符串翻轉 函數接口 */
@FunctionalInterface
public interface FunctionStringReverse {    
   String reverse(String v);
}

Java 中一個接口的實現有2種方式,<font color="#f12242">匿名內部類</font>(記到這個),子類實現

  1. FunctionStringReverse functionStringReverse = new FunctionStringReverse() {
         @Override
         public String reverse(String v) {
             return null;
         }
    };
  2. public class SubClass implements FunctionStringReverse{
         @Override
         public String reverse(String v) {
             return null;
         }
    }

lambda 表達式的結構.以下:

() -> {}java

  • () 表明請求參數ide

    • 單參數時能夠省略括號()
  • ->
  • {} 函數體(能夠理解爲<font color="#f12242">函數接口惟一方法</font>體中的處理邏輯,lambda 表達式必須調用這個惟一的方法,因此能夠忽略該方法的名字)函數

    • 方法體只有一條語句時能夠省略大括號{}
    • 方法體只有一條語句且有返回值時能夠省略return 和 {}

2、進階

示例1:寫一個接口函數並使用lambda語法糖實現

/** 1. 字符串打印 函數接口 */
@FunctionalInterface
public interface FunctionStringPrintf {    
   void printf(String v);
}
@Slf4j
public class LambdaTest {
    
    @Test
    public void lambdaStringPrintf() {
        //2. 實現接口的匿名函數方法
        FunctionStringPrintf f = (x) -> log.info("lambda string printf:{}", x);
        //3. 把接口當成一個實參參數傳遞
        func1(f, "abcdefg");
        //4. 跟上面兩行是同樣的效果,這種書寫更加簡單
        func1((x) -> log.info("lambda string printf:{}", x), "hijklmn");
        /*
        * 5. 靜態方法引用(直白點講,就是使用已經寫好的靜態方法,例如工具類字符串反轉打印,         * 由於工具類已經提供了這個方法,就不該該在匿名內部類中再寫一次該實現,這是多餘的,*         * 因此直接引用已有方法便可)
        */
        func1(LambdaTest::printf, "hijklmn");
        //6. 5.中靜態方法的引用另一種實現,5.中的更簡潔)
        func1((x) -> LambdaTest.printf(x), "hijklmn");
    }
    /** 7. (這個很重要,很重要,很重要-->理解) */
    private void func1(FunctionStringPrintf f, String p) {
        f.printf(p);
    }
    /** 8. 提供一個打印字符串的靜態方法*/
    private static void printf(String p) {
        log.info("static method reference printf:{}", p);
    }
    /** 9. 提供一個打印字符串的非靜態方法*/
    private void noStaticPrintf(String p) {
        log.info("static method reference printf:{}", p);
    }
}
  1. 按照上面的代碼就實現了一個lambda語法的函數接口工具

    • 上述步驟7:FunctionStringPrintf f 這是一個函數接口,只要傳遞進來的方法符合接口函數中的方法就均可以調用。<font color="gren">即2. 中 (x) -> log.info("lambda string printf:{}", x); 有入參無返回,跟1.中接口函數中惟一的方法void printf(String v)正好(該接口也是有入參無返回)能對應上。</font>那麼就能使用方法引用來實現(上述5.和8.就是靜態方法的引用實現)

引申出4種模式的方法引用,如圖下:

類型描述 示例 代碼示例
靜態方法引用 類::靜態方法名 LambdaTest::printf
某個對象的實例方法引用 實例對象::方法名 new LambdaTest()::noStaticPrintf
某個類型的任意對象的實例方法引用 String::toString() String::compareToIgnoreCase()
構造方法引用 類::new LambdaTest::new

第三種:某個類型的任意對象的實例方法引用code

這種類型是感受是針對Java基本類型、包裝類型和String這類而言,若是是這幾種狀況,能夠像靜態方法引用同樣使用,只是這些方法的實現不是staitc而已。

第四種:構造方法引用對象

@FunctionalInterface
public interface FunctionConstruct {
    LambdaMethodReferenceTest construct(String p);
}

這種類型的函數接口中的惟一方法須要返回實例對象接口

相關文章
相關標籤/搜索