天天看點

java基礎學習_JDK新特性_day28總結

java基礎學習_JDK新特性_day28總結

=============================================================================
=============================================================================
涉及到的知識點有:
    0:JDK5 & JDK7 新特性
    1:Java 8 新特性
    2:Java 9 新特性
    3:Java 10 新特性
=============================================================================
=============================================================================
0:JDK5 & JDK7 新特性
    (1) JDK5新特性
        自動裝箱和拆箱(day13)
        泛型(day16)
        增強for循環(day16)
        靜态導入(day16)
        可變參數(day16)
        枚舉(day27)
--------------------------------------        
    (2) JDK7新特性
        二進制字面量(二進制的表現形式)
        數字字面量可以出現下劃線(用_分隔資料)
        switch語句的表達式可是用字元串(day04)
        泛型簡化(泛型推斷(也叫菱形泛型))
        異常的多個catch合并(多catch的使用)(day19)
        try-with-resources 語句(自動釋放資源的用法)
-----------------------------------------------------------------------------
1:Java 8 新特性
    (1) 接口中有方法了(可以有預設方法、靜态方法、私有方法(JDK9))。
-----------------------------------------------------------------------------
    (2) Lambda表達式
        A: 接口的實作類的目的是:為了給接口中的方法找方法體。即為了使用方法體,不得不去定義一個實作類。
            你以為這是理所當然的,其實不是。
            
            對于某些場景,我能不能有一種更加先進,更加清亮的方法呢? 
            答:有,函數式程式設計。(Lambda表達式程式設計)
--------------------------------------        
        B: 從Java 8 開始,沒有實作類的接口,也可以直接使用接口了。如何使用? 
            答:Lambda表達式。
            其實就像Lambda表達式替代了實作類一樣。
--------------------------------------        
        C: Java語言中使用Lambda表達式的前提是:必須有"函數式接口"。
    
            函數式接口:有且僅有一個抽象方法的接口,叫做函數式接口。

            如何才能萬無一失地檢測一下目前接口是不是函數式接口呢?
            用一個固定的格式寫在public interface的前一行即可。
            
            格式:
                @FunctionalInterface 
                public interface 函數式接口名 {
                ...
                }
                
                @FunctionalInterface 
                注解:在java.lang包中
                
            注意:
                不管寫不寫@FunctionalInterface,隻要有且僅有一個抽象方法的接口就是函數式接口!
                但是呢?建議永遠寫上。
--------------------------------------                
        D: Lambda表達式要想使用,一定要有函數式接口的推斷環境。
            推斷環境?
                方式1. 要麼通過方法的參數類型,來确定是哪個函數式接口。
                方式2. 要麼通過指派操作,指派語句左側的資料類型,來确定是哪個函數式接口。
                    
                    // 通過方法的參數類型,來确定是哪個函數式接口。
                    // 在調用方法的時候,方法的參數類型是函數式接口,是以Lambda可以推斷出來是哪個接口。
                    method((int a, int b) -> {
                        return a + b;
                    });
                    
                    // 通過指派操作,指派語句左側的資料類型,來确定是哪個函數式接口。(指派語句左側的類型來進行Lambda上下文推斷)
                    Calculator cal = (int a, int b) -> {
                        return a + b;
                    };
                    method(cal);
                    
                    // 錯誤寫法!沒有上下文環境,Lambda就無法推斷是哪個函數式接口。
                    /*
                    (int a, int b) -> {
                        return a + b;
                    };
                    */
        
            Lambda的格式就是為了将抽象方法,翻譯成以下三點:
                1. 一些參數(方法參數)
                2. 一個箭頭
                3. 一些代碼(方法體)
            例如這個抽象方法:
                public abstract int sum(int a, int b);
                翻譯成為Lambda的标準格式:
                (int a, int b) -> { 
                    return a + b; 
                } 
--------------------------------------                
        E: Lambda的簡便格式
            在Lambda表達式當中,凡是可以推斷的,都是可以省略的。
                1. Lambda表達式當中的參數類型可以省略不寫。
                2. 如果參數有且僅有一個,那麼可以省略小括号。
                3. 如果語句隻有一條,那麼大括号、分号和return也可以省略。
                
                // Lambda表達式的标準格式
                method((int x) -> {
                    return ++x;
                });

                // 簡化格式1:省略參數類型:Lambda表達式當中的參數類型可以省略不寫。
                method((x) -> {
                    return ++x;
                });

                // 簡化格式2:再省略小括号:如果參數有且僅有一個,那麼可以省略小括号。
                method(x -> {
                    return ++x;
                });

                // 簡化格式3:再省略大括号和return:如果語句隻有一條,那麼大括号、分号和return也可以省略。
                method(x -> ++x);                            
-----------------------------------------------------------------------------                
    (3) 方法引用
        Lambda表達式的備援場景:
            在某些場景下,Lambda表達式要做的事情,在另一個地方已經寫過了(即已有方法體了,已經實作了)。
            那麼此時如果通過Lambda表達式重複編寫相同的代碼,就是浪費。
    
        那麼此時如何才能複用已經存在的方法邏輯呢?
            JDK8中新特性:方法引用(為了簡化Lambda而存在)
            即:如果Lambda表達式需要做的事情,在另一個類當中已經做過了,那麼就可以直接拿過來替換Lambda。這種方式叫做方法引用。
        
        方法引用的格式:
            1.通過類名引用靜态方法,格式:類名::靜态方法名    
        方法引用的格式:
            2.通過對象名引用靜态方法,格式:對象名::成員方法名    
        還有其他的格式:
            ...
        小結:
            1. 一定要先有函數式接口,才能使用Lambda表達式。
            2. 對于Lambda表達式使用的備援場景,可以使用方法引用來進行簡化。
-----------------------------------------------------------------------------
    (4) Stream API 流式操作
        集合for周遊的備援場景:
--------------------------------------        
        Stream流式思想概述:
            像流水線操作一般執行。從其他語言中借鑒過來的。可以很友善的操作多個元素。
            即簡化了普通的集合操作。
--------------------------------------            
        擷取Stream流對象的常用方式:
            Java 8當中的“流”其實就是Stream接口的對象。
            JDK提供了一個流接口:java.util.stream.Stream<T>
        如何擷取Stream流對象?
            1. 根據集合擷取流對象
                集合名稱.stream();
            2. 根據數組擷取流對象,數組當中的元素必須是引用類型才行
                Stream.of(數組名稱);
--------------------------------------                
        擷取Stream流對象後如何使用map方法呢?
            我們擷取流對象後,可以使用映射方法:map(用于轉換的Lambda表達式)
            映射:就是将一個對象轉換成另一個對象,把老對象映射到新對象上。
            舉例:"趙麗穎,98"    轉換成為    "98"    把一個長字元串轉換為一個短字元串
                    "98"        轉換成為    98        把一個字元串轉化成為一個int數字    
--------------------------------------        
        如果希望對流對象當中的元素進行過濾,可以使用過濾方法:filter(能産生boolean結果的lambda表達式)
            如果參數Lambda産生了true,則要該元素;如果産生了false,則不要該元素。    
--------------------------------------
        如果希望在流當中進行元素的周遊操作,可以使用forEach方法:forEach(Lambda表達式)
            意思是:對流當中的每一個元素都要進行操作。
            注意:參數Lambda表達式必須是一個能夠消費一個參數,而且不産生資料結果(無傳回值)的Lambda表達式。
            例如:
                Lambda:        s -> System.out.println(s);
                方法引用:        System::println            
--------------------------------------        
        流當中的元素如果特别多,那麼隻有一個人在逐一、挨個處理,肯定比較慢、費勁。
        如果對流當中的元素,使用多個人同時處理,這就是“并行”。
            parallel    并行,平行
        Java 8中将并行進行了優化,我們可以很容易的對資料進行并行操作。
        Stream API可以聲明性地通過parallel()與sequential()在并行流與順序流之間進行切換。            
        
        如何擷取“并行流”?
            .parallelStream()        // 直接擷取
            .stream.parallel()       // 間接擷取

        注意事項:
            1. 使用并行流操作的時候,到底有幾個人進行同時操作呢?我們不用管,JDK自己處理。(用的是Fork/Join架構)
            2. 隻要正确使用的話,就不會出現多個人搶到同一個元素的情況。    
-----------------------------------------------------------------------------            
2:Java 9 新特性                
    (1) 子產品化思想概述
        1. 把整體分成部分(子產品)。檔案體積變小。
        2. 在子產品中增權重限控制。權限控制更精确。
            如下圖所示:

(2) 認識module-info.java檔案
            如下圖所示:
(3) 将Eclipse項目改造為子產品
        選擇項目右鍵 --> Configure --> Create module-info.java --> xxx.mod(子產品命名不推薦使用數字)
        再配置好module-info.java檔案中的exports和requires。
    (4) 設定子產品間的依賴關系
        1. 在module-info.java檔案中先加入requires語句(最底層包名)。
        2. 選中項目右擊 --> Build Path --> Configure Build Path... --> Projects --> Modulepath --> Add... --> 選中所依賴的項目(該步驟是Ecplise所特有的)
-----------------------------------------------------------------------------                
3:Java 10 新特性
    Java 10 新特新連結:        https://juejin.im/entry/5ab1c64951882555880545f2               
=============================================================================      

我的GitHub位址:

https://github.com/heizemingjun

我的部落格園位址:

http://www.cnblogs.com/chenmingjun

我的螞蟻筆記部落格位址:

http://blog.leanote.com/chenmingjun

Copyright ©2018 黑澤明軍

【轉載文章務必保留出處和署名,謝謝!】

繼續閱讀