Java8->Java19的初步探索

導(dǎo)讀

最近網(wǎng)上開始了大量的關(guān)于Java19的討論,我也想著用了Java8這么久該接受一點(diǎn)新的東西了,于是便開始研究了起來

Java 19

Java19是一個(gè)免費(fèi)版本海蔽。下面是JDK19的支持圖

image.png

(來源:https://www.bilibili.com/video/BV1V84y1B7dD?t=39.9
可以看到目前較為長(zhǎng)期的免費(fèi)支持版本是Java17,而下一個(gè)版本是Java21(免費(fèi)支持于2027年結(jié)束)

開始研究

在網(wǎng)上查找了大量的文件并對(duì)JDK9-19做了些整理打算從以下幾個(gè)功能去了解從Java8-Java19的發(fā)展

  1. 數(shù)組轉(zhuǎn)列表和列表轉(zhuǎn)數(shù)組(Java 9)
  2. var關(guān)鍵字(Java 10)
  3. yield關(guān)鍵字(Java 13)
  4. Record(記錄)類(Java 14)
  5. case的多個(gè)值匹配(Java 14)
  6. case返回值(Java 14,17)
  7. Sealed(密閉)類(Java 15)
  8. switch類型判斷(Java 17)
  9. 文本塊(Java 17)
  10. switch復(fù)雜表達(dá)式(Java 19 第三次預(yù)覽(正式版Java 19該功能被移除狂塘,不排除以后會(huì)加入的可能))

數(shù)組轉(zhuǎn)列表和列表轉(zhuǎn)數(shù)組(Java 9)

@Test
    public void test(){
        String[] strings={"你好","早","這foe及","vdsoijfdois"};
        List<String> stringList=List.of(strings);//JDK9
        System.out.println(stringList);
    }

List.of為JDK9帶來的新功能,他可以將數(shù)組轉(zhuǎn)換為對(duì)應(yīng)的列表(List)鳄厌,但是荞胡,轉(zhuǎn)換后的List是不能改變的。

var關(guān)鍵字(Java 10)

var關(guān)鍵字可以不用顯式地聲明變量的類型了嚎。舉例:

public class People{
    private String name;
    private int age;
    //Getter Setter...
}
public static void main(String[] args){
    var people=new Student();
    people.setSid("321321");
    //...
}

雖說不會(huì)顯示地聲明類型泪漂,但實(shí)際上,變量的類型是確定的歪泳,因?yàn)椋?/p>

  1. 使用var聲明的變量必須被初始化
  2. 初始化時(shí)是什么類型以后再賦值時(shí)必須是這個(gè)類型或者這個(gè)類的子類

yield關(guān)鍵字(Java 13)

yield目前貌似只適用于case分支中萝勤,舉例:

@Test
    public void returedSwitch2(){
        Scanner scanner=new Scanner(System.in);
        int i = scanner.nextInt();
        int result=switch (i){
            case 1->{
                System.out.printf("輸入的是%d",i);
                yield i+3;
            }
            case 2->{
                System.out.printf("輸入的是%d呀",i);
                yield i-5;
            }
            default -> i;
        };
        System.out.printf("result=%d",result);
    }

它的作用是將case分支中yield后面的值作為返回值返回回來。如果要使用yield關(guān)鍵字或者想讓switch返回一個(gè)值則case后面的:必須被替換為->呐伞。
->這個(gè)符號(hào)在switch中的應(yīng)用是Java 12帶來的敌卓,它的作用是讓case的執(zhí)行唯一,直白說就是不會(huì)再“逢break土媲猓”趟径。
舉個(gè)例子:

Scanner scanner=new Scanner(System.in);
        String next = scanner.next();
        //part 1
        String response=switch (next){
            case "你好","早上好","中午好","下午好"->"你好呀";
            case "我不是很好","我不好","我難受"->"不要傷心嘛";
            default -> "需要幫助嗎?";
        };
        System.out.println(response);
        System.out.println("與上面的對(duì)比");
        //part 2
        switch (next){
            case "你好","早上好","中午好","下午好":
                System.out.println("你好呀");
            case "我不是很好","我不好","我難受":System.out.println("不要傷心嘛");break;
            default :System.out.println("需要幫助嗎癣防?") ;break;
        };

part 1就是新的switch語(yǔ)法蜗巧,它避免了大量的break出現(xiàn)在代碼中,如果case "你好","早上好","中午好","下午好"滿足劣砍,則返回"你好呀"惧蛹,而不像原來那樣把所有結(jié)果都返回。對(duì)于同一個(gè)需求刑枝,part1的寫法顯然比part2的寫法方便一些香嗓。

Record(記錄)類(Java 14)

record關(guān)鍵字可以將某個(gè)類標(biāo)識(shí)為記錄類,被該關(guān)鍵字標(biāo)記的類會(huì)自動(dòng)生成Getter和Setter以及hashCode()装畅,toString()方法靠娱,同時(shí),該類的值不會(huì)再被改變掠兄!
舉例:

//Record類只能這么定義
public record StudentRecord(String id, String name, int age) {
  
}
@Test
    public void recordClass(){
        StudentRecord sr=new StudentRecord("123","張三",12);
        System.out.println(sr);
        System.out.printf("""
                id:%s,姓名:%s
                年齡:%d
                """,sr.id(),sr.name(),sr.age());
    }

這個(gè)類在前后端分離項(xiàng)目中是很有用的像云。

case的多個(gè)值匹配(Java 14)與case返回值(Java 14锌雀,17)

其實(shí)從Java 12開始就對(duì)switch進(jìn)行改動(dòng)了,在Java 14中迅诬,switch可以對(duì)多個(gè)值進(jìn)行比較了腋逆,相比于以前的case 1:case 2...這種簡(jiǎn)化了很多,在yield關(guān)鍵字章節(jié)使用的就是這個(gè)特性侈贷。

String response=switch (next){
            case "你好","早上好","中午好","下午好"->"你好呀";
            case "我不是很好","我不好","我難受"->"不要傷心嘛";
            default -> "需要幫助嗎惩歉?";
        };

下面的寫法也是正確的

  switch (next){
            case "你好","早上好","中午好","下午好":System.out.println("你好呀");
            case "我不是很好","我不好","我難受":System.out.println("不要傷心嘛");
            default :System.out.println( "需要幫助嗎?");
        };

第一個(gè)寫法是可以將"你好呀"俏蛮、"不要傷心嘛"這類字符串作為switch返回值賦值給response的撑蚌。
第二個(gè)寫法則只能進(jìn)行多值匹配,switch沒辦法返回任何值搏屑,原因可以參見yield關(guān)鍵字章節(jié)

Sealed(密閉)類(Java 15)

有時(shí)候可能不希望某個(gè)接口或者類被某個(gè)類實(shí)現(xiàn)或者繼承争涌,那么,密閉類就可以滿足這個(gè)要求辣恋。

public sealed interface AnimalMethods permits Animal{
    public void call();
}
public sealed class Animal implements AnimalMethods permits Sheep,Cow{
    private String name;
    private int age;
    private Date birthDate;
    //Getter,Setter...
    @Override
    public void call() {
        System.out.println("任何動(dòng)物都有叫聲");
    }
}
public non-sealed class Sheep extends Animal{
    @Override
    public void call() {
        System.out.println("咩~");
    }
}
public non-sealed class Cow extends Animal{
    @Override
    public void call() {
        System.out.println("牟~");
    }
}

首先我定義了一個(gè)密閉接口AnimalMethods并限制只能讓Animal類或者接口來實(shí)現(xiàn)或者繼承它亮垫。
然后創(chuàng)建一個(gè)類Animal實(shí)現(xiàn)接口AnimalMethods,同時(shí)Animal類也是一個(gè)密閉類抑党,要求只有Sheep類和Cow類可以繼承這個(gè)類包警。
最后創(chuàng)建SheepCow類。

密閉類有這樣的性質(zhì):

  1. seald關(guān)鍵字不能和final以及record關(guān)鍵字一起使用
  2. seald關(guān)鍵字必須和permits關(guān)鍵字一起使用
  3. 密閉類必須有子類且必須限制所有子類底靠,密閉接口必須有子接口或者實(shí)現(xiàn)類并且限制所有子接口以及實(shí)現(xiàn)類。
    以上面的代碼為例特铝,將 public sealed class Animal implements AnimalMethods permits Sheep,Cow改為public sealed class Animal implements AnimalMethods permits Sheep同時(shí)保持繼承關(guān)系不變暑中,那么會(huì)編譯失敗,因?yàn)椋?code>Cow類也是Animal類的子類鲫剿,因此permites也必須包含Cow
  4. 使用seald標(biāo)記的類或接口其子類或子接口必須是seald鳄逾、non-seald(非密閉)、final中的一種

switch類型判斷(Java 17)

switch可以代替instanceof關(guān)鍵字對(duì)對(duì)象的類型進(jìn)行判斷灵莲。
需要注意的是雕凹,在Java 19正式版中并不支持這個(gè)功能。

Object number=new Student();
        //這個(gè)功能目前在孵化中
        var result=switch (number){
            case null-> "啊哦";
            case Integer i->"int";
            case Student s->"Student";
            default -> "Oops";
        };
        System.out.println(result);

這確實(shí)是一個(gè)很大的改進(jìn)政冻,希望以后可以實(shí)裝

文本塊(Java 17)

在Record(記錄)類(Java 14)章節(jié)可以看到文本塊的影子枚抵,使用"""(3個(gè)英文雙引號(hào))就可以定義一個(gè)文本塊。它的目的是為了解決“使用+鏈接帶有轉(zhuǎn)義字符的字符串導(dǎo)致的代碼難看的問題明场∑。”
在以前,想要輸出含有轉(zhuǎn)義字符的字符串同時(shí)還要方便代碼編寫是不可能的苦锨,只能通過+完成逼泣,比如:

public static void main(String[] args){
    System.out.printf("姓名:%s"+
    "性別:%c"+
    "年齡:%d","張三",'m',18);
}

很痛苦趴泌,這樣寫代碼很難看,有了文本塊后就可以這么寫:

public static void main(String[] args){
    System.out.printf("""
    姓名:%s
    性別:%c
    年齡:%d
    ""","張三",'m',18);
}

方便了很多拉庶,而且代碼也不是很難看嗜憔。
(你問我printf是新功能嗎?——不是J险獭)

switch復(fù)雜表達(dá)式(Java 19 第三次預(yù)覽(正式版Java 19該功能被移除痹筛,不排除以后會(huì)加入的可能))

你是否被大量的if-else所困擾?現(xiàn)在廓鞠,解決方案來了帚稠,你可以使用switch進(jìn)行表達(dá)式的判斷了。

Student student=new Student();
        student.setAge(12);
        String result= switch (student){
            case Student s when s.getAge()>=18->"已成年";
            default -> "未成年";
        };
        System.out.println(result);
Student student=new Student();
student.setAge(12);
if(student.getAge>=18){
  System.out.println("已成年");
else{
  System.out.println("未成年");
}

這個(gè)例子很簡(jiǎn)單床佳,如果你要進(jìn)行多種判斷的話無疑這種寫法是最方便的也更整潔滋早。
但是,在正式的Java19中不支持這個(gè)功能砌们。

評(píng)價(jià)

以上只是介紹了這些新特性的一小部分杆麸,實(shí)際上,這幾個(gè)版本都對(duì)性能浪感、開發(fā)復(fù)雜程度做了一定的優(yōu)化昔头。同時(shí),也讓Java的開發(fā)變得簡(jiǎn)單了一些影兽。
關(guān)于市場(chǎng):由于目前國(guó)內(nèi)大部分的公司所開發(fā)的項(xiàng)目使用的還是Java 8揭斧。因此,市場(chǎng)上在相當(dāng)長(zhǎng)的一段時(shí)間內(nèi)還是會(huì)青睞Java 8峻堰。所以對(duì)于小白而言還是以Java 8的學(xué)習(xí)為主讹开,高版本的Java感興趣的話可以自己去了解。
對(duì)于框架:Springboot 3已經(jīng)明確要求使用Java 17以上捐名,因此旦万,在不久的將來,如果依然使用Springboot開發(fā)的話那么Java 8會(huì)被淘汰掉镶蹋。由于Java 19剛剛發(fā)布不久成艘,很多框架(如Mybatis-plus)還沒有做支持,所以贺归,最近不要使用Java19+Springboot做一些項(xiàng)目淆两,過一段時(shí)間之后再看看。

代碼

https://blacol.lanzoue.com/iysxK0ibyxgd

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末牧氮,一起剝皮案震驚了整個(gè)濱河市琼腔,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌踱葛,老刑警劉巖丹莲,帶你破解...
    沈念sama閱讀 216,372評(píng)論 6 498
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件光坝,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡甥材,警方通過查閱死者的電腦和手機(jī)盯另,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,368評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來洲赵,“玉大人鸳惯,你說我怎么就攤上這事〉迹” “怎么了芝发?”我有些...
    開封第一講書人閱讀 162,415評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)苛谷。 經(jīng)常有香客問我辅鲸,道長(zhǎng),這世上最難降的妖魔是什么腹殿? 我笑而不...
    開封第一講書人閱讀 58,157評(píng)論 1 292
  • 正文 為了忘掉前任独悴,我火速辦了婚禮,結(jié)果婚禮上锣尉,老公的妹妹穿的比我還像新娘刻炒。我一直安慰自己,他們只是感情好自沧,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,171評(píng)論 6 388
  • 文/花漫 我一把揭開白布坟奥。 她就那樣靜靜地躺著,像睡著了一般暂幼。 火紅的嫁衣襯著肌膚如雪筏勒。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,125評(píng)論 1 297
  • 那天旺嬉,我揣著相機(jī)與錄音,去河邊找鬼厨埋。 笑死邪媳,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的荡陷。 我是一名探鬼主播雨效,決...
    沈念sama閱讀 40,028評(píng)論 3 417
  • 文/蒼蘭香墨 我猛地睜開眼,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼废赞!你這毒婦竟也來了徽龟?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 38,887評(píng)論 0 274
  • 序言:老撾萬榮一對(duì)情侶失蹤唉地,失蹤者是張志新(化名)和其女友劉穎据悔,沒想到半個(gè)月后传透,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,310評(píng)論 1 310
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡极颓,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,533評(píng)論 2 332
  • 正文 我和宋清朗相戀三年朱盐,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片菠隆。...
    茶點(diǎn)故事閱讀 39,690評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡兵琳,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出骇径,到底是詐尸還是另有隱情躯肌,我是刑警寧澤,帶...
    沈念sama閱讀 35,411評(píng)論 5 343
  • 正文 年R本政府宣布破衔,位于F島的核電站清女,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏运敢。R本人自食惡果不足惜校仑,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,004評(píng)論 3 325
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望传惠。 院中可真熱鬧迄沫,春花似錦、人聲如沸卦方。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,659評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)盼砍。三九已至尘吗,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間浇坐,已是汗流浹背睬捶。 一陣腳步聲響...
    開封第一講書人閱讀 32,812評(píng)論 1 268
  • 我被黑心中介騙來泰國(guó)打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留近刘,地道東北人擒贸。 一個(gè)月前我還...
    沈念sama閱讀 47,693評(píng)論 2 368
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像觉渴,于是被迫代替她去往敵國(guó)和親介劫。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,577評(píng)論 2 353

推薦閱讀更多精彩內(nèi)容