0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

函數(shù)式接口的應(yīng)用知識(shí)點(diǎn)

科技綠洲 ? 來源:Java技術(shù)指北 ? 作者:Java技術(shù)指北 ? 2023-10-13 11:32 ? 次閱讀

概述

函數(shù)式接口將分為三個(gè)篇章來為大家介紹:

  • (應(yīng)用篇一)(1)函數(shù)式接口的來源,(2)Lambda表達(dá)式,(3)雙冒號(hào)運(yùn)算符
  • (應(yīng)用篇二)(4)詳細(xì)介紹@FunctionInterface注解(5)對(duì)java.util.function包進(jìn)行解讀
  • (原理篇)介紹函數(shù)式接口的實(shí)現(xiàn)原理 應(yīng)用篇將階段相關(guān)的JDK源碼以及給出典型的示例代碼 原理篇?jiǎng)t從編譯、JVM維度來分析函數(shù)式接口的實(shí)現(xiàn)原理,具有一定深度,需要讀者具備一定的底層知識(shí)。

說明:源碼使用的版本為JDK-11.0.11

FunctionInterface

這一節(jié),指北君給大家介紹如何聲明一個(gè)函數(shù)式接口,F(xiàn)unctionInterface注解就是用于來干這件事情的,當(dāng)我們?yōu)榻涌谠黾覨unctionInterface注解后,編譯器會(huì)按照函數(shù)式接口的約束進(jìn)行檢查。先看看注解的定義:

@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
public @interface FunctionalInterface {}

源碼顯示該注解可用于類、接口和枚舉類型,注解應(yīng)用于運(yùn)行時(shí)階段。

如果僅從代碼層面我們可能會(huì)犯錯(cuò)誤,比如如下情況:

@FunctionalInterface
public interface IFuncInterfaceSample{
  void func1();
  void func2();
}

我們會(huì)發(fā)現(xiàn)編譯器報(bào)錯(cuò)了,這是因?yàn)樵谠O(shè)計(jì)FunctionInterface的時(shí)候還增加了額外的約束,這些約束無法在注解的定義中呈現(xiàn),是通過編譯器實(shí)現(xiàn)的,下面指北君就一一為小伙伴們道來。

首先、FunctionInterface是SAM接口,什么是SAM接口呢?全稱Single Abstract Method,從英文字義我們就能明白,接口中只能有一個(gè)抽象方法。由于Java在接口中增加了對(duì)默認(rèn)方法和靜態(tài)方法的支持,因此采用SAM設(shè)計(jì)的接口也可以定義默認(rèn)方法和靜態(tài)方法,也就是說我們在使用了FunctionInterface注解的接口中還能夠定義默認(rèn)方法和靜態(tài)方法。除了默認(rèn)方法和靜態(tài)方法外,這里還有一種列外,我們查看java.util.Comparator源碼

@FunctionalInterface
public interface Comparator< T > {
    int compare(T o1, T o2);
    boolean equals(Object obj);
    ...

咦,這怎么回事,不是說只能有一個(gè)抽象方法么?小伙伴們仔細(xì)觀察接口會(huì)發(fā)現(xiàn)其中一個(gè)是equals接口,這不是Object中的方法么?是的,這就是另一條特殊的約束,如果抽象方法是覆蓋的是Object的方法,則不計(jì)入抽象方法的個(gè)數(shù)。

除了抽象方法的個(gè)數(shù)限制外FunctionInterface只能用于interface,不能用于class和enum,對(duì)于這種情形編譯器也會(huì)報(bào)錯(cuò)。

小伙伴們有沒想過FunctionInterface為什么要有上面提到的約束呢?相信有些已經(jīng)隱隱感覺到了:Java是通過類來實(shí)現(xiàn)函數(shù)式編程的(這部分內(nèi)容將在原理篇中說明)。

最后,還有一個(gè)重點(diǎn)知識(shí):是不是只有使用了@FunctionalInterface才能作為函數(shù)式接口呢?相信有不少伙伴和指北君之前一樣理所當(dāng)然地覺得顯然應(yīng)該是這樣嘛。但是,JDK的世界很精妙:只要符合函數(shù)式接口約束條件的接口,即使沒有采用@FunctionalInterface,編譯器都會(huì)處理成函數(shù)式接口,比如下面的示例代碼:

public interface IFuncInterfaceWithoutAn {
  boolean test(int i);
}

public class Demo {
  public static void main(String args[]) {
    IFuncInterfaceWithoutAn whithout = (x)- >x%2==1;
    System.out.println(whithout.test(3));
  }
}

java.util.function

之前的學(xué)習(xí),指北君介紹了什么是函數(shù)式編程,如果寫一段Lambda表達(dá)式,以及學(xué)習(xí)如何申明函數(shù)式接口。本節(jié)我們將學(xué)習(xí)JDK為我們提供的基礎(chǔ)函數(shù)式接口,這些接口位于java.util.function包中,它們可以滿足我們很多通用場景的使用需要。

圖片
function包

打開java.util.function包,我們發(fā)現(xiàn)里面足足有43個(gè)接口,這43個(gè)接口就是JDK提供給我們43把劍,如果要讓小伙伴舞動(dòng)這43把劍,是不是感覺鴨梨山大了呢?小伙伴們,別慌!在你看完指北君后面的分析后,你就可以將這43把劍化為無形,做到手中無劍心中有劍。

指北君先帶領(lǐng)小伙伴們對(duì)接口名稱進(jìn)行分析。是的,是接口名稱,不是源碼

圖片
接口名稱解析

從思維導(dǎo)圖中可以看到,接口的主體為最后的單詞,包含:Consumer,F(xiàn)unction,Predicate,Supplier,Operator。

圖片
接口主體類別

除了主體外,小伙伴是不是還看到了Unary,Binary,Bi這種表示參數(shù)個(gè)數(shù)的修飾詞。

修飾詞作用
Unary一元
Binary二元
BiBinary縮寫

再就剩下參數(shù)類型和方向的修飾詞和參數(shù)方向Int,Long,Double,Obj,(X)To(Y)。

通過以上解析,我們可以確定所有的接口都是用于描述函數(shù)的輸入?yún)?shù)和返回,這就是java.util.function留在我們心中終極大劍。有了這把終極武器,我們可以對(duì)于這43把劍信手拈來,也隨意創(chuàng)造自己的武器,當(dāng)然,要?jiǎng)?chuàng)造新的武器,按照這43把劍依葫蘆畫瓢是可以,但是要打造精品武器還需要掌握我們接下來介紹的FunctionInterface接口了。

在對(duì)整個(gè)java.util.function包了然于胸后,我們再打開一個(gè)典型的接口看看源碼。function包中的類型都為接口類型,并且使用了@FunctionInterface注解,且每個(gè)接口都且只有一個(gè)接口(抽象)方法,部分接口存在默認(rèn)方法和靜態(tài)方法。

@FunctionalInterface
public interface Consumer< T > {

    /**
     * Performs this operation on the given argument.
     *
     * @param t the input argument
     */
    void accept(T t);

    /**
     * Returns a composed {@code Consumer} that performs, in sequence, this
     * operation followed by the {@code after} operation. If performing either
     * operation throws an exception, it is relayed to the caller of the
     * composed operation.  If performing this operation throws an exception,
     * the {@code after} operation will not be performed.
     *
     * @param after the operation to perform after this operation
     * @return a composed {@code Consumer} that performs in sequence this
     * operation followed by the {@code after} operation
     * @throws NullPointerException if {@code after} is null
     */
    default Consumer< T > andThen(Consumer< ? super T > after) {
        Objects.requireNonNull(after);
        return (T t) - > { accept(t); after.accept(t); };
    }
}

accept為核心接口方法,andThen為方便復(fù)雜組合場景提供的默認(rèn)方法。function包的整個(gè)代碼邏輯都很簡潔易懂,部分Operator繼承了Function,指北君就不一一贅述了。

小結(jié)

至此,函數(shù)式接口的應(yīng)用知識(shí)點(diǎn)已經(jīng)介紹和分析完,涵蓋知識(shí)點(diǎn)包含:java.util.function包,F(xiàn)unctionInterface注解,Lambda表達(dá)式,雙冒號(hào)操作符等知識(shí)點(diǎn)。函數(shù)式接口在集合,流中應(yīng)用較為廣泛,也證明了其在數(shù)據(jù)時(shí)候的顯著優(yōu)勢,各位小伙伴可以結(jié)合這些JDK中的源碼進(jìn)行鞏固加深。

聲明:本文內(nèi)容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問題,請聯(lián)系本站處理。 舉報(bào)投訴
  • 接口
    +關(guān)注

    關(guān)注

    33

    文章

    8372

    瀏覽量

    150565
  • 源碼
    +關(guān)注

    關(guān)注

    8

    文章

    630

    瀏覽量

    29077
  • 函數(shù)
    +關(guān)注

    關(guān)注

    3

    文章

    4262

    瀏覽量

    62243
  • 代碼
    +關(guān)注

    關(guān)注

    30

    文章

    4700

    瀏覽量

    68108
  • JDK
    JDK
    +關(guān)注

    關(guān)注

    0

    文章

    80

    瀏覽量

    16566
收藏 人收藏

    評(píng)論

    相關(guān)推薦

    嵌入C語言知識(shí)點(diǎn)總結(jié)

    怎么才能做好嵌入開發(fā)?學(xué)好C語言吧!今天就來推薦一篇大佬寫的嵌入C語言知識(shí)點(diǎn)總結(jié)。
    發(fā)表于 09-27 09:53 ?1148次閱讀

    嵌入內(nèi)存管理的知識(shí)點(diǎn)總結(jié)

    任何程序運(yùn)行起來都需要分配內(nèi)存空間存放該進(jìn)程的資源信息的,C程序也不例外。C程序中的變量、常量、函數(shù)、代碼等等的信息所存放的區(qū)域都有所不同,不同的區(qū)域又有不同的特性。C語言學(xué)習(xí)者、尤其是在學(xué)習(xí)嵌入的朋友,這些知識(shí)點(diǎn)一定要吃透!
    發(fā)表于 08-17 09:33 ?448次閱讀
    嵌入<b class='flag-5'>式</b>內(nèi)存管理的<b class='flag-5'>知識(shí)點(diǎn)</b>總結(jié)

    嵌入C/單片機(jī)C/標(biāo)準(zhǔn)C知識(shí)點(diǎn)

    :嵌入C、標(biāo)準(zhǔn)C、單片機(jī)C區(qū)別  知識(shí)點(diǎn)2:程序組成和程序原則  知識(shí)點(diǎn)3:變量類型(函數(shù)、數(shù)組、指針、結(jié)構(gòu)體等類型)  知識(shí)點(diǎn)4:常用的
    發(fā)表于 10-24 14:42

    工程師總結(jié)了一些C語言的知識(shí)點(diǎn)

    僅供大家參考,想一起和我討論嗎,可以加一下我的QQ2685896890,黃老師一、嵌入C/單片機(jī)C/標(biāo)準(zhǔn)C知識(shí)點(diǎn)知識(shí)點(diǎn)1:嵌入C、標(biāo)準(zhǔn)C、單片機(jī)C區(qū)別知識(shí)點(diǎn)2:程序組成和程序原則
    發(fā)表于 07-25 10:23

    【信盈達(dá)】C語言知識(shí)點(diǎn)的總結(jié)

    一、嵌入C/單片機(jī)C/標(biāo)準(zhǔn)C知識(shí)點(diǎn)知識(shí)點(diǎn)1:嵌入C、標(biāo)準(zhǔn)C、單片機(jī)C區(qū)別知識(shí)點(diǎn)2:程序組成和程序原則知識(shí)點(diǎn)3:變量類型(
    發(fā)表于 10-08 14:41

    STM32外部中斷知識(shí)點(diǎn)概述

    STM32外部中斷概述知識(shí)點(diǎn)(1)知識(shí)點(diǎn)(2)知識(shí)點(diǎn)(3)中斷服務(wù)函數(shù)外部中斷常用庫函數(shù)外部中斷的一般配置步驟
    發(fā)表于 08-16 07:43

    C語言程序小知識(shí)點(diǎn)總結(jié)

    C語言總結(jié)(stm32嵌入開發(fā))文章目錄C語言總結(jié)(stm32嵌入開發(fā))c程序小知識(shí)點(diǎn)總結(jié)1.靜態(tài)變量static與外部變量extern的使用2.函數(shù)封裝后返回值的方法3.軟件寄存
    發(fā)表于 11-05 07:45

    RK3399 HDMI接口知識(shí)點(diǎn)匯總,絕對(duì)實(shí)用

    RK3399 HDMI接口知識(shí)點(diǎn)匯總,絕對(duì)實(shí)用
    發(fā)表于 03-07 06:53

    高一數(shù)學(xué)知識(shí)點(diǎn)總結(jié)

    高一數(shù)學(xué)知識(shí)點(diǎn)總結(jié)高一數(shù)學(xué)知識(shí)點(diǎn)總結(jié)高一數(shù)學(xué)知識(shí)點(diǎn)總結(jié)
    發(fā)表于 02-23 15:27 ?0次下載

    高二數(shù)學(xué)知識(shí)點(diǎn)總結(jié)

    高二數(shù)學(xué)知識(shí)點(diǎn)總結(jié)高二數(shù)學(xué)知識(shí)點(diǎn)總結(jié)高二數(shù)學(xué)知識(shí)點(diǎn)總結(jié)
    發(fā)表于 02-23 15:27 ?0次下載

    液晶屏知識(shí)點(diǎn)培訓(xùn)

    液晶屏知識(shí)點(diǎn)液晶屏分辨率等,液晶屏接口
    發(fā)表于 01-01 08:00 ?42次下載

    PWM知識(shí)點(diǎn)詳解

    PWM知識(shí)點(diǎn)
    發(fā)表于 03-16 08:00 ?44次下載

    嵌入知識(shí)點(diǎn)總結(jié)

    嵌入知識(shí)點(diǎn)總結(jié)(arm嵌入開發(fā)led過程)-嵌入知識(shí)點(diǎn)總結(jié)? ? ? ? ? ? ? ? ? ??
    發(fā)表于 07-30 14:20 ?23次下載
    嵌入<b class='flag-5'>式</b><b class='flag-5'>知識(shí)點(diǎn)</b>總結(jié)

    數(shù)字電路知識(shí)點(diǎn)總結(jié)

    本文整理了數(shù)字電路課程中的相關(guān)基本的知識(shí)點(diǎn)和較為重要的知識(shí)點(diǎn),用于求職的數(shù)電部分的知識(shí)準(zhǔn)備,差缺補(bǔ)漏。
    的頭像 發(fā)表于 05-30 15:07 ?4477次閱讀
    數(shù)字電路<b class='flag-5'>知識(shí)點(diǎn)</b>總結(jié)

    什么是函數(shù)接口

    、及其所使用的一些和函數(shù)接口相關(guān)的知識(shí)點(diǎn)進(jìn)行一個(gè)全面的學(xué)習(xí)。函數(shù)
    的頭像 發(fā)表于 10-13 14:48 ?1384次閱讀
    什么是<b class='flag-5'>函數(shù)</b><b class='flag-5'>式</b><b class='flag-5'>接口</b>