最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Java 函數(shù)式編程要點總結

 更新時間:2021年06月18日 11:40:05   作者:知了一笑  
函數(shù)式編程并不是Java新提出的概念,其與指令編程相比,強調(diào)函數(shù)的計算比指令的計算更重要;與過程化編程相比,其中函數(shù)的計算可以隨時調(diào)用。Java8新引入函數(shù)式編程方式,大大的提高了編碼效率。本文將對涉及的對象等進行統(tǒng)一的學習及記錄。

一、函數(shù)式概念

函數(shù)式編程是一種結構化編程的范式,主要思想是把運算過程盡量寫成系列嵌套的函數(shù)調(diào)用。函數(shù)編程的概念表述帶有很抽象的感覺,可以基于案例看:

public class Function01 {
    public static void main(String[] args) {
        // 運算:(x+y)* c
        int x1 = 2 ;
        int y1 = 3 ;
        int c1 = 4 ;
        int sum1 = x1 + y1 ;
        int res1 = sum1 * c1 ;
        System.out.println("res1 = "+res1);
    }
}

這里基于過程的方式做計算,上面的代碼塊著重在描述程序執(zhí)行過程。

在看基于函數(shù)的方式解決方法:

public class Function02 {
    public static void main(String[] args) {
        // 函數(shù)式計算
        System.out.println("func01 = "+func01(2,3,4));
    }
    private static int func01 (int x,int y,int c){
        return (x+y)*c;
    }
}

函數(shù)式編程的核心要素:傳入?yún)?shù),執(zhí)行邏輯,返回值,也可以沒有返回值。

函數(shù)式的編程風格側(cè)重描述程序的執(zhí)行邏輯,不是執(zhí)行過程。

同上面計算過程相比,函數(shù)式編程也減少很多臨時變量的創(chuàng)建,代碼風格也變的簡潔清楚。

二、函數(shù)與方法

在Java語言中有函數(shù)式編程風格,但是Java代碼中沒有函數(shù)的說法,而是稱為:方法;

public class Function03 {
    public static void main(String[] args) {
        Func03 func03 = new Func03();
        func03.add(2);
        System.out.println(func03.res1);
    }
}
class Func03 {
    public int res1 = 0 ;
    public void add (int a1){
        this.res1 = a1 +1 ;
    }
}

類定義引用數(shù)據(jù)類型,類實例化后的對象可以調(diào)用類內(nèi)部的方法和數(shù)據(jù),這是最直觀的感覺。

但是方法又有靜態(tài)和非靜態(tài)的區(qū)別,靜態(tài)方法屬于類所有,類實例化前即可使用。

非靜態(tài)方法可以訪問類中的任何成員變量和方法,并且必須是類實例化后的對象才可以調(diào)用。

三、JDK函數(shù)基礎

1、Lambda表達式

Lambda表達式也可稱為閉包,是推動Java8發(fā)布的最重要新特性,允許把函數(shù)作為一個方法的參數(shù)(函數(shù)作為參數(shù)傳遞進方法中)。

這里就很鮮明的對比Lambda表達式語法和傳統(tǒng)用法。

public class Lambda01 {
    interface LambdaOpera {
        int operation(int a, int b);
    }
    public static void main(String[] args) {
        LambdaOpera lambdaOpera = new LambdaOpera(){
            @Override
            public int operation(int a, int b) {
                return a * b ;
            }
        };
        System.out.println(lambdaOpera.operation(3,2));
        LambdaOpera lambdaOpera01 = (int a, int b) -> a + b;
        LambdaOpera lambdaOpera02 = (int a, int b) -> a - b;
        System.out.println(lambdaOpera01.operation(3,2));
        System.out.println(lambdaOpera02.operation(3,2));
    }
}

在看一個直觀的應用案例,基于Lambda的方式創(chuàng)建線程,可以使代碼變的更加簡潔緊湊:

public class Lambda02 {
    public static void main(String[] args) {
        new Thread(new Runnable() {
            @Override
            public void run() {
                for (int i = 0; i < 2; i++) {
                    System.out.println(i);
                }
            }
        }).start();
        // 對比 Lambda 方式
        new Thread(() -> {
            for (int i = 0; i < 2; i++) {
                System.out.println(i);
            }
        }).start();
    }
}

在看一下Runnable接口的結構:

FunctionalInterface標記在接口上,表示該接口是函數(shù)式接口,并且該接口只包含一個抽象方法,

@FunctionalInterface
public interface Runnable {
    public abstract void run();
}

Lambda表達式本身可以理解為就是一個接口的實現(xiàn)過程,這里runnable就是完整的Lambda表達式聲明:

public class Lambda04 {
    public static void main(String[] args) {
        Runnable runnable = () -> {
            System.out.println("run one...");
        };
        Thread thread = new Thread(runnable);
        thread.start();
    }
}

Lambda表達式最直觀的作用就是使得代碼變得異常簡潔,并且可以作為參數(shù)傳遞。

2、函數(shù)式接口

Lambda表達式雖然有很多優(yōu)點,但是使用的時候需要定義一些接口用來完成編碼,這樣又使得表達式又變得重量級,Java8自身已經(jīng)提供幾個常見的函數(shù)式接口。

  • Function:輸入一個參數(shù),返回一個結果;
  • Consumer:輸入一個參數(shù),不返回結果;
  • BiFunction:輸入兩個參數(shù),返回一個結果;
  • BiConsumer:輸入兩個參數(shù),不返回任何結果;
public class Lambda05 {
    public static void main(String[] args) {
        Function<Integer, Integer> function01 = x -> x * 2;
        System.out.println(function01.apply(2));
        BiFunction<Integer, Integer, Integer> function02 = (x, y) -> x * y;
        System.out.println(function02.apply(2, 3));

        Consumer<String> consumer01 = msg -> System.out.println("msg:"+msg);
        consumer01.accept("hello");

        BiConsumer<String,Integer> consumer02 = (msg,i)
                -> System.out.println(msg+":"+i);
        consumer02.accept("world",3);
    }
}

如果面對更復雜的業(yè)務需求,可以自定義函數(shù)式接口去解決。

四、Optional類

1、Null判斷

Optional類是Java函數(shù)式編程的應用,主要用來解決常見的空指針異常問題。

在Java編程的開發(fā)中,很多地方都能常見空指針異常的拋出,如果想避免這個問題就要加入很多判斷:

public class Optional01 {
    public static void main(String[] args) {
        User user = new User(1,"hello") ;
        if (user != null){
            if (user.getName() != null){
                System.out.println(user.getName());
            }
        }
    }
}

為了確保程序不拋出空指針這種低級的錯誤,在程序中隨處可以null的判斷,代碼顯然冗余和繁雜。

2、Optional應用

基于Optional類創(chuàng)建的對象可能包含空值和null值,也同樣會拋出對應的異常:

public class Optional02 {
    public static void main(String[] args) {
        // NoSuchElementException
        Optional<User> optionalUser = Optional.empty();
        optionalUser.get();
        // NullPointerException
        Optional<User> nullOpt = Optional.of(null);
        nullOpt.get();
    }
}

所以在不明確對象的具體情況下,使用ofNullable()方法:

public class Optional03 {
    public static void main(String[] args) {
        User user = new User(1,"say");
        Optional<User> optionalUser = Optional.ofNullable(user);
        if (optionalUser.isPresent()){
            System.out.println(optionalUser.get().getName());
        }
        User user1 = null ;
        User createUser = Optional.ofNullable(user1).orElse(createUser());
        System.out.println(createUser.getName());
        User user2 = null ;
        Optional.ofNullable(user2).orElseThrow( ()
                -> new RuntimeException());;
    }
    public static User createUser (){
        return new User(2,"hello") ;
    }
}

這樣看下來Optional結合鏈式方法和Lambda表達式就很大程度上簡化了應用的代碼量:

public class Optional04 {
    public static void main(String[] args) {
        // 1、map轉(zhuǎn)換方法
        User user = new User(99, "Java");
        // user = null ;
        String name = Optional.ofNullable(user)
                .map(u -> u.getName()).orElse("c++");
        System.out.println(name);
        // 2、過濾方法
        Optional<User> optUser01 = Optional.ofNullable(user)
                .filter(u -> u.getName() != null && u.getName().contains("c++"));
        // NoSuchElementException
        System.out.println(optUser01.get().getName());
    }
}

Optional提供null處理的各種方法,可以簡潔很多代碼判斷,但是在使用風格上和之前變化很大。

五、Stream流

如果Optional簡化很多Null的判斷,那Stream流的API則簡化了很多集合的遍歷判斷,同樣也是基于函數(shù)式編程。

上述為Stream接口繼承關系如圖,同樣提供一些特定接口和較大的包裝接口,通過源碼查看,可以看到和函數(shù)編程也是密切相關。

public class Stream01 {
    public static void main(String[] args) {
        Stream<String> stream = Stream.of("hello", "java");
        stream.forEach(str -> System.out.print(str+";"));
    }
}

Stream與函數(shù)接口結合使用,函數(shù)接口又可以使用Lambda表達式進行簡化代碼。在Java8通過Stream可以大量簡化集合使用的代碼復雜度。

public class Stream02 {
    public static void main(String[] args) {
        // 1、轉(zhuǎn)換Stream
        List<String> list = Arrays.asList("java+;", "c++;", "net;");
        list.stream();
        // 2、forEach操作
        list.stream().forEach(System.out::print);
        // 3、map映射,輸出 3,4
        IntStream.rangeClosed(2,3).map(x->x+1).forEach(System.out::println);
        // 4、filter過濾
        list.stream().filter(str -> str.contains("+")).forEach(System.out::print);
        // 5、distinct去重
        Integer[] arr = new Integer[]{3, 1, 3, 1, 2,4};
        Stream.of(arr).distinct().forEach(System.out::println);
        // 6、sorted排序
        Stream.of(arr).sorted().forEach(System.out::println);
        // 7、collect轉(zhuǎn)換
        List<String> newList = list.stream().filter(str -> str.contains("+"))
                .collect(Collectors.toList());
        newList.stream().forEach(System.out::print);
    }
}

在沒有Stream相關API之前,對于集合的操作和遍歷都會產(chǎn)生大量的代碼,通過Stream相關API集合的函數(shù)式編程和Lambda表達式的風格,簡化集合很多操作。

六、源代碼地址

GitHub·地址
https://github.com/cicadasmile/java-base-parent
GitEE·地址
https://gitee.com/cicadasmile/java-base-parent

以上就是Java 函數(shù)式編程要點總結的詳細內(nèi)容,更多關于Java 函數(shù)式編程的資料請關注腳本之家其它相關文章!

相關文章

  • Java編寫簡易rabbitmq生產(chǎn)者與消費者的代碼

    Java編寫簡易rabbitmq生產(chǎn)者與消費者的代碼

    開發(fā)時經(jīng)常與其它系統(tǒng)用rabbitmq對接,當需要自測時,還是自己寫rabbitmq生產(chǎn)者、消費者自測方便些,下面給大家總結使用java編寫簡易rabbitmq的方法,感興趣的朋友一起看看吧
    2023-11-11
  • Springboot?上傳文件或頭像(MultipartFile、transferTo)

    Springboot?上傳文件或頭像(MultipartFile、transferTo)

    本文主要介紹了Springboot?上傳文件或頭像(MultipartFile、transferTo),文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2023-04-04
  • Spring Boot使用Druid進行維度的統(tǒng)計和監(jiān)控

    Spring Boot使用Druid進行維度的統(tǒng)計和監(jiān)控

    這篇文章主要介紹了Spring Boot使用Druid進行維度的統(tǒng)計和監(jiān)控,非常不錯,具有參考借鑒價值,需要的朋友可以參考下
    2017-04-04
  • 淺談SpringSecurity重寫默認配置

    淺談SpringSecurity重寫默認配置

    這篇文章主要介紹了SpringSecurity重寫默認配置,包括注入Bean、擴展WebSecurityConfigurerAdapter、重寫端點授權配置及實現(xiàn)AuthenticationProvider,感興趣的可以了解一下
    2025-01-01
  • spring?boot集成loback日志配置的示例代碼

    spring?boot集成loback日志配置的示例代碼

    這篇文章主要介紹了spring?boot集成loback日志配置的示例代碼,本文通過示例代碼給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友參考下吧
    2024-01-01
  • 關于mybatis-plus-generator的簡單使用示例詳解

    關于mybatis-plus-generator的簡單使用示例詳解

    在springboot項目中集成mybatis-plus是很方便開發(fā)的,最近看了一下plus的文檔,簡單用一下它的代碼生成器,接下來通過實例代碼講解關于mybatis-plus-generator的簡單使用,感興趣的朋友跟隨小編一起看看吧
    2024-03-03
  • springboot如何使用thymeleaf模板訪問html頁面

    springboot如何使用thymeleaf模板訪問html頁面

    springboot中推薦使用thymeleaf模板,使用html作為頁面展示。那么如何通過Controller來訪問來訪問html頁面呢?下面通過本文給大家詳細介紹,感興趣的朋友跟隨腳本之家小編一起看看吧
    2018-05-05
  • 如何在Java中優(yōu)雅地判空詳解

    如何在Java中優(yōu)雅地判空詳解

    這篇文章主要大家介紹了關于如何在Java中優(yōu)雅地判空的相關資料,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2018-11-11
  • 詳解SpringBoot的三種緩存技術(Spring Cache、Layering Cache 框架、Alibaba JetCache 框架)

    詳解SpringBoot的三種緩存技術(Spring Cache、Layering Cache 框架、Alibaba J

    這篇文章主要介紹了SpringBoot的三種緩存技術,幫助大家更好的理解和學習springboot框架,感興趣的朋友可以了解下
    2020-10-10
  • 解決spring-data-jpa mysql建表編碼問題

    解決spring-data-jpa mysql建表編碼問題

    這篇文章主要介紹了解決spring-data-jpa mysql建表編碼問題,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2021-07-07

最新評論

渭源县| 西华县| 南康市| 兰西县| 无锡市| 叶城县| 手机| 库尔勒市| 岢岚县| 泾源县| 军事| 阳高县| 泾阳县| 建瓯市| 普陀区| 古蔺县| 济阳县| 九龙县| 千阳县| 瓮安县| 丰台区| 济宁市| 武邑县| 利辛县| 阆中市| 苍梧县| 灵武市| 新巴尔虎左旗| 门源| 南京市| 海口市| 西林县| 高青县| 兰州市| 浠水县| 孝感市| 潜山县| 富阳市| 洛川县| 新余市| 罗江县|