国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

這篇具有很好參考價值的文章主要介紹了JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)。希望對大家有所幫助。如果存在錯誤或未考慮完全的地方,請大家不吝賜教,您也可以點擊"舉報違法"按鈕提交疑問。

1. 新語法結(jié)構(gòu)

新的語法結(jié)構(gòu),勾勒出了 Java 語法進化的一個趨勢,將開發(fā)者從復(fù)雜、繁瑣的低層次抽象中逐漸解放出來,以更高層次、更優(yōu)雅的抽象,既降低代碼量,又避免意外編程錯誤的出現(xiàn),進而提高代碼質(zhì)量和開發(fā)效率。

1.1 Java的REPL工具: jShell命令

JDK9的新特性

Java 終于擁有了像Python 和 Scala 之類語言的REPL工具(交互式編程環(huán)境,read - evaluate - print - loop):jShell。以交互式的方式對語句和表達式進行求值。即寫即得、快速運行。

利用jShell在沒有創(chuàng)建類的情況下,在命令行里直接聲明變量,計算表達式,執(zhí)行語句。無需跟人解釋”public static void main(String[] args)”這句"廢話"。

使用舉例

  • 調(diào)出jShell

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

  • 獲取幫助

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

  • 基本使用

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

  • 導(dǎo)入指定的包

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

  • 默認已經(jīng)導(dǎo)入如下的所有包:(包含java.lang包)

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

  • 只需按下 Tab 鍵,就能自動補全代碼

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

  • 列出當(dāng)前 session 里所有有效的代碼片段

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

  • 查看當(dāng)前 session 下所有創(chuàng)建過的變量

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

  • 查看當(dāng)前 session 下所有創(chuàng)建過的方法

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

Tips:我們還可以重新定義相同方法名和參數(shù)列表的方法,即對現(xiàn)有方法的修改(或覆蓋)。

  • 使用外部代碼編輯器來編寫 Java 代碼

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

從外部文件加載源代碼【HelloWorld.java】

public void printHello() {
    System.out.println("馬上周末了,祝大家周末快樂!");
}
printHello();

  • 使用/open命令調(diào)用

  • 退出jShell

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

1.2 異常處理之try-catch資源關(guān)閉

在JDK7 之前,這樣處理資源的關(guān)閉:

@Test
public void test01() {
    FileWriter fw = null;
    BufferedWriter bw = null;
    try {
        fw = new FileWriter("d:/1.txt");
        bw = new BufferedWriter(fw);

        bw.write("hello");
    } catch (IOException e) {
        e.printStackTrace();
    } finally {
        try {
            if (bw != null) {
                bw.close();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        try {
            if (fw != null) {
                fw.close();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }

    }
}

JDK7的新特性

try的后面可以增加一個(),在括號中可以聲明流對象并初始化。try中的代碼執(zhí)行完畢,會自動把流對象釋放,就不用寫finally了。

格式:

try(資源對象的聲明和初始化){
    業(yè)務(wù)邏輯代碼,可能會產(chǎn)生異常
}catch(異常類型1 e){
    處理異常代碼
}catch(異常類型2 e){
    處理異常代碼
}

說明:

1、在try()中聲明的資源,無論是否發(fā)生異常,無論是否處理異常,都會自動關(guān)閉資源對象,不用手動關(guān)閉了。

2、這些資源實現(xiàn)類必須實現(xiàn)AutoCloseableCloseable接口,實現(xiàn)其中的close()方法。CloseableAutoCloseable的子接口。Java7幾乎把所有的“資源類”(包括文件IO的各種類、JDBC編程的ConnectionStatement等接口…)都進行了改寫,改寫后資源類都實現(xiàn)了AutoCloseableCloseable接口,并實現(xiàn)了close()方法。

3、寫到try()中的資源類的變量默認是 final 聲明的,不能修改。

舉例:

//舉例1
@Test
public void test02() {
    try (
        FileWriter fw = new FileWriter("d:/1.txt");
        BufferedWriter bw = new BufferedWriter(fw);
    ) {
        bw.write("hello");
    } catch (IOException e) {
        e.printStackTrace();
    }
}

//舉例2
@Test
public void test03() {
    //從d:/1.txt(utf-8)文件中,讀取內(nèi)容,寫到項目根目錄下1.txt(gbk)文件中
    try (
        FileInputStream fis = new FileInputStream("d:/1.txt");
        InputStreamReader isr = new InputStreamReader(fis, "utf-8");
        BufferedReader br = new BufferedReader(isr);

        FileOutputStream fos = new FileOutputStream("1.txt");
        OutputStreamWriter osw = new OutputStreamWriter(fos, "gbk");
        BufferedWriter bw = new BufferedWriter(osw);
    ) {
        String str;
        while ((str = br.readLine()) != null) {
            bw.write(str);
            bw.newLine();
        }
    } catch (FileNotFoundException e) {
        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    }
}

JDK9的新特性

try的前面可以定義流對象,try后面的()中可以直接引用流對象的名稱。在try代碼執(zhí)行完畢后,流對象也可以釋放掉,也不用寫finally了。

格式:

A a = new A();
B b = new B();
try(a;b){
    可能產(chǎn)生的異常代碼
}catch(異常類名 變量名){
    異常處理的邏輯
}

舉例:

@Test
public void test04() {
    InputStreamReader reader = new InputStreamReader(System.in);
    OutputStreamWriter writer = new OutputStreamWriter(System.out);
    try (reader; writer) {
        //reader是final的,不可再被賦值
        //   reader = null;

    } catch (IOException e) {
        e.printStackTrace();
    }
}

1.3 局部變量類型推斷

JDK 10的新特性

局部變量的顯示類型聲明,常常被認為是不必須的,給一個好聽的名字反而可以很清楚的表達出下面應(yīng)該怎樣繼續(xù)。本新特性允許開發(fā)人員省略通常不必要的局部變量類型聲明,以增強Java語言的體驗性、可讀性。

  • 使用舉例
//1.局部變量的實例化
var list = new ArrayList<String>();

var set = new LinkedHashSet<Integer>();

//2.增強for循環(huán)中的索引
for (var v : list) {
    System.out.println(v);
}

//3.傳統(tǒng)for循環(huán)中
for (var i = 0; i < 100; i++) {
    System.out.println(i);
}

//4. 返回值類型含復(fù)雜泛型結(jié)構(gòu)
var iterator = set.iterator();
//Iterator<Map.Entry<Integer, Student>> iterator = set.iterator();

  • 不適用場景
    • 聲明一個成員變量
    • 聲明一個數(shù)組變量,并為數(shù)組靜態(tài)初始化(省略new的情況下)
    • 方法的返回值類型
    • 方法的參數(shù)類型
    • 沒有初始化的方法內(nèi)的局部變量聲明
    • 作為catch塊中異常類型
    • Lambda表達式中函數(shù)式接口的類型
    • 方法引用中函數(shù)式接口的類型

代碼舉例:

聲明一個成員變量,并初始化值為null

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

聲明一個數(shù)組變量,并為數(shù)組靜態(tài)初始化(省略new的情況下)

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

沒有初始化的方法內(nèi)的局部變量聲明

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

方法的返回值類型

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

方法的參數(shù)類型

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

構(gòu)造器的參數(shù)類型

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

作為catch塊中異常類型

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

Lambda表達式中函數(shù)式接口的類型

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

方法引用中函數(shù)式接口的類型

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

注意:

  • var不是一個關(guān)鍵字,而是一個類型名,將它作為變量的類型。不能使用 var 作為類名。

  • 這不是JavaScript。var并不會改變 Java是一門靜態(tài)類型語言的事實。編譯器負責(zé)推斷出類型,并把結(jié)果寫入字節(jié)碼文件,就好像是開發(fā)人員自己敲入類型一樣。

1.4 instanceof的模式匹配

JDK14中預(yù)覽特性:

instanceof 模式匹配通過提供更為簡便的語法,來提高生產(chǎn)力。有了該功能,可以減少Java程序中顯式強制轉(zhuǎn)換的數(shù)量,實現(xiàn)更精確、簡潔的類型安全的代碼。

Java 14之前舊寫法:

if(obj instanceof String){
    String str = (String)obj; //需要強轉(zhuǎn)
    .. str.contains(..)..
}else{
    ...
}

Java 14新特性寫法:

if(obj instanceof String str){
    .. str.contains(..)..
}else{
    ...
}

舉例:

/**
 * instanceof的模式匹配(預(yù)覽)
 *
 * @author shkstart
 * @create 上午 11:32
 */
public class Feature01 {
    @Test
    public void test1(){

        Object obj = new String("hello,Java14");
        obj = null;//在使用null 匹配instanceof 時,返回都是false.
        if(obj instanceof String){
            String str = (String) obj;
            System.out.println(str.contains("Java"));
        }else{
            System.out.println("非String類型");
        }

        //舉例1:
        if(obj instanceof String str){ //新特性:省去了強制類型轉(zhuǎn)換的過程
            System.out.println(str.contains("Java"));
        }else{
            System.out.println("非String類型");
        }
    }
}

// 舉例2
class InstanceOf{

    String str = "abc";

    public void test(Object obj){

        if(obj instanceof String str){//此時的str的作用域僅限于if結(jié)構(gòu)內(nèi)。
            System.out.println(str.toUpperCase());
        }else{
            System.out.println(str.toLowerCase());
        }

    }
}

//舉例3:
class Monitor{
    private String model;
    private double price;

//    public boolean equals(Object o){
//        if(o instanceof Monitor other){
//            if(model.equals(other.model) && price == other.price){
//                return true;
//            }
//        }
//        return false;
//    }


    public boolean equals(Object o){
        return o instanceof Monitor other && model.equals(other.model) && price == other.price;
    }

}

JDK15中第二次預(yù)覽:

沒有任何更改。

JDK16中轉(zhuǎn)正特性:

在Java16中轉(zhuǎn)正。

1.5 switch表達式

傳統(tǒng)switch聲明語句的弊端:

  • 匹配是自上而下的,如果忘記寫break,后面的case語句不論匹配與否都會執(zhí)行; —>俗稱:case穿透
  • 所有的case語句共用一個塊范圍,在不同的case語句定義的變量名不能重復(fù);
  • 不能在一個case里寫多個執(zhí)行結(jié)果一致的條件;
  • 整個switch不能作為表達式返回值;
//常見錯誤實現(xiàn)
switch(month){
    case 3|4|5://3|4|5 用了位運算符,11 | 100 | 101結(jié)果是 1117
        System.out.println("春季");
        break;
    case 6|7|8://6|7|8用了位運算符,110 | 111 | 1000結(jié)果是111115
        System.out.println("夏季");
        break;
    case 9|10|11://9|10|11用了位運算符,1001 | 1010 | 1011結(jié)果是101111
        System.out.println("秋季");
        break;
    case 12|1|2://12|1|2 用了位運算符,1100 | 1 | 10 結(jié)果是1111,是15
        System.out.println("冬季");
        break;
    default:
        System.out.println("輸入有誤");
}

JDK12中預(yù)覽特性:

  • Java 12將會對switch聲明語句進行擴展,使用case L ->來替代以前的break;,省去了 break 語句,避免了因少寫 break 而出錯。

  • 同時將多個 case 合并到一行,顯得簡潔、清晰,也更加優(yōu)雅的表達邏輯分支。

  • 為了保持兼容性,case 條件語句中依然可以使用字符 : ,但是同一個 switch 結(jié)構(gòu)里不能混用 -> : ,否則編譯錯誤。

舉例:

Java 12之前

public class SwitchTest {
    public static void main(String[] args) {
        int numberOfLetters;
        Fruit fruit = Fruit.APPLE;
        switch (fruit) {
            case PEAR:
                numberOfLetters = 4;
                break;
            case APPLE:
            case GRAPE:
            case MANGO:
                numberOfLetters = 5;
                break;
            case ORANGE:
            case PAPAYA:
                numberOfLetters = 6;
                break;
            default:
                throw new IllegalStateException("No Such Fruit:" + fruit);
        }
        System.out.println(numberOfLetters);

    }
}
enum Fruit {
    PEAR, APPLE, GRAPE, MANGO, ORANGE, PAPAYA;
}

switch 語句如果漏寫了一個 break,那么邏輯往往就跑偏了,這種方式既繁瑣,又容易出錯。

Java 12中:

public class SwitchTest1 {
    public static void main(String[] args) {
        Fruit fruit = Fruit.GRAPE;
        switch(fruit){
            case PEAR -> System.out.println(4);
            case APPLE,MANGO,GRAPE -> System.out.println(5);
            case ORANGE,PAPAYA -> System.out.println(6);
            default -> throw new IllegalStateException("No Such Fruit:" + fruit);
        };
    }
}

更進一步:

public class SwitchTest2 {
    public static void main(String[] args) {
        Fruit fruit = Fruit.GRAPE;
        int numberOfLetters = switch(fruit){
            case PEAR -> 4;
            case APPLE,MANGO,GRAPE -> 5;
            case ORANGE,PAPAYA -> 6;
            default -> throw new IllegalStateException("No Such Fruit:" + fruit);
        };
        System.out.println(numberOfLetters);
    }
}

JDK13中二次預(yù)覽特性:

JDK13中引入了yield語句,用于返回值。這意味著,switch表達式(返回值)應(yīng)該使用yieldswitch語句(不返回值)應(yīng)該使用break。

yieldreturn的區(qū)別在于:return會直接跳出當(dāng)前循環(huán)或者方法,而yield只會跳出當(dāng)前switch塊。

在以前:

@Test
public void testSwitch1(){
    String x = "3";
    int i;
    switch (x) {
        case "1":
            i=1;
            break;
        case "2":
            i=2;
            break;
        default:
            i = x.length();
            break;
    }
    System.out.println(i);
}

在JDK13中:

@Test
public void testSwitch2(){
    String x = "3";
    int i = switch (x) {
        case "1" -> 1;
        case "2" -> 2;
        default -> {
            yield 3;
        }
    };
    System.out.println(i);
}

或者

@Test
public void testSwitch3() {
    String x = "3";
    int i = switch (x) {
        case "1":
            yield 1;
        case "2":
            yield 2;
        default:
            yield 3;
    };
    System.out.println(i);
}

JDK14中轉(zhuǎn)正特性:

這是JDK 12和JDK 13中的預(yù)覽特性,現(xiàn)在是正式特性了。

JDK17的預(yù)覽特性:switch的模式匹配

舊寫法:

static String formatter(Object o) {
    String formatted = "unknown";
    if (o instanceof Integer i) {
        formatted = String.format("int %d", i);
    } else if (o instanceof Long l) {
        formatted = String.format("long %d", l);
    } else if (o instanceof Double d) {
        formatted = String.format("double %f", d);
    } else if (o instanceof String s) {
        formatted = String.format("String %s", s);
    }
    return formatted;
}

模式匹配新寫法:

static String formatterPatternSwitch(Object o) {
    return switch (o) {
        case Integer i -> String.format("int %d", i);
        case Long l    -> String.format("long %d", l);
        case Double d  -> String.format("double %f", d);
        case String s  -> String.format("String %s", s);
        default        -> o.toString();
    };
}

直接在 switch 上支持 Object 類型,這就等于同時支持多種類型,使用模式匹配得到具體類型,大大簡化了語法量,這個功能很實用。

1.6 文本塊

現(xiàn)實問題:

在Java中,通常需要使用String類型表達 HTMLXML,SQLJSON 等格式的字符串,在進行字符串賦值時需要進行轉(zhuǎn)義和連接操作,然后才能編譯該代碼,這種表達方式難以閱讀并且難以維護。

JDK13的新特性

使用"""作為文本塊的開始符和結(jié)束符,在其中就可以放置多行的字符串,不需要進行任何轉(zhuǎn)義。因此,文本塊將提高Java程序的可讀性和可寫性。

基本使用:

"""
line1
line2
line3
"""

相當(dāng)于:

"line1\nline2\nline3\n"

或者一個連接的字符串:

"line1\n" +
"line2\n" +
"line3\n"

如果字符串末尾不需要行終止符,則結(jié)束分隔符可以放在最后一行內(nèi)容上。例如:

"""
line1
line2
line3"""

相當(dāng)于

"line1\nline2\nline3"

文本塊可以表示空字符串,但不建議這樣做,因為它需要兩行源代碼:

String empty = """
""";

舉例1:普通文本

原有寫法:

 String text1 = "The Sound of silence\n" +
                "Hello darkness, my old friend\n" +
                "I've come to talk with you again\n" +
                "Because a vision softly creeping\n" +
                "Left its seeds while I was sleeping\n" +
                "And the vision that was planted in my brain\n" +
                "Still remains\n" +
                "Within the sound of silence";

System.out.println(text1);

使用新特性:

String text2 = """
                The Sound of silence
                Hello darkness, my old friend
                I've come to talk with you again
                Because a vision softly creeping
                Left its seeds while I was sleeping
                And the vision that was planted in my brain
                Still remains
                Within the sound of silence
                """;
System.out.println(text2);

舉例2:HTML語句

<html>
  <body>
      <p>Hello, JDK</p>
  </body>
</html>

將其復(fù)制到Java的字符串中,會展示成以下內(nèi)容:

"<html>\n" +
"    <body>\n" +
"        <p>Hello, JDK</p>\n" +
"    </body>\n" +
"</html>\n";

即被自動進行了轉(zhuǎn)義,這樣的字符串看起來不是很直觀,在JDK 13中:

"""
<html>
  <body>
      <p>Hello, world</p>
  </body>
</html>
""";

舉例3:SQL語句

select employee_id,last_name,salary,department_id
from employees
where department_id in (40,50,60)
order by department_id asc

原有方式:

String sql = "SELECT id,NAME,email\n" +
                "FROM customers\n" +
                "WHERE id > 4\n" +
                "ORDER BY email DESC";

使用新特性:

String sql1 = """
                SELECT id,NAME,email
                FROM customers
                WHERE id > 4
                ORDER BY email DESC
                """;

舉例4:JSON字符串

原有方式:

String myJson = "{\n" +
                "    \"name\":\"Song Hongkang\",\n" +
                "     \"address\":\"xy5462.blog.csdn.net\",\n" +
                "    \"email\":\"shkstart@126.com\"\n" +
                "}";
System.out.println(myJson);

使用新特性:

String myJson1 = """
                {
                    "name":"Song Hongkang",
                     "address":"xy5462.blog.csdn.net",
                    "email":"shkstart@126.com"
                }""";
System.out.println(myJson1);

JDK14中二次預(yù)覽特性

JDK14的版本主要增加了兩個escape sequences,分別是 \ <line-terminator>\s escape sequence。

舉例:

public class Feature05 {
    //jdk14新特性
    @Test
    public void test5(){
        String sql1 = """
                SELECT id,NAME,email
                FROM customers
                WHERE id > 4
                ORDER BY email DESC
                """;
        System.out.println(sql1);

        // \:取消換行操作
        // \s:表示一個空格
        String sql2 = """
                SELECT id,NAME,email \
                FROM customers\s\
                WHERE id > 4 \
                ORDER BY email DESC
                """;
        System.out.println(sql2);
    }
}

JDK15中功能轉(zhuǎn)正

1.7 Record

背景

早在2019年2月份,Java 語言架構(gòu)師 Brian Goetz,曾寫文抱怨“Java太啰嗦”或有太多的“繁文縟節(jié)”。他提到:開發(fā)人員想要創(chuàng)建純數(shù)據(jù)載體類(plain data carriers)通常都必須編寫大量低價值、重復(fù)的、容易出錯的代碼。如:構(gòu)造函數(shù)、getter/setter、equals()hashCode()以及toString()等。

以至于很多人選擇使用IDE的功能來自動生成這些代碼。還有一些開發(fā)會選擇使用一些第三方類庫,如Lombok等來生成這些方法。

JDK14中預(yù)覽特性:神說要用record,于是就有了。 實現(xiàn)一個簡單的數(shù)據(jù)載體類,為了避免編寫:構(gòu)造函數(shù),訪問器,equals(),hashCode () ,toString ()等,Java 14推出 record

record 是一種全新的類型,它本質(zhì)上是一個 final 類,同時所有的屬性都是 final 修飾,它會自動編譯出 public get 、hashcodeequals、toString、構(gòu)造器等結(jié)構(gòu),減少了代碼編寫量。

具體來說:當(dāng)你用record 聲明一個類時,該類將自動擁有以下功能:

  • 獲取成員變量的簡單方法,比如下面示例中的 name()partner() 。注意區(qū)別于我們平常getter()的寫法。
  • 一個 equals 方法的實現(xiàn),執(zhí)行比較時會比較該類的所有成員屬性。
  • 重寫 hashCode() 方法。
  • 一個可以打印該類所有成員屬性的 toString() 方法。
  • 只有一個構(gòu)造方法。

此外:

  • 還可以在record聲明的類中定義 靜態(tài)字段、靜態(tài)方法構(gòu)造器實例方法。

  • 不能record聲明的類中 定義實例字段類不能聲明為abstract;不能聲明顯式的父類等。

舉例1(舊寫法)

class Point {
    private final int x;
    private final int y;

    Point(int x, int y) {
        this.x = x;
        this.y = y;
    }

    int x() {
        return x;
    }

    int y() {
        return y;
    }

    public boolean equals(Object o) {
        if (!(o instanceof Point)) return false;
        Point other = (Point) o;
        return other.x == x && other.y == y;
    }

    public int hashCode() {
        return Objects.hash(x, y);
    }

    @Override
    public String toString() {
        return "Point{" +
                "x=" + x +
                ", y=" + y +
                '}';
    }
}

舉例1(新寫法)

record Point(int x, int y) { }

舉例1

public record Dog(String name, Integer age) {
}
public class Java14Record {

    public static void main(String[] args) {
        Dog dog1 = new Dog("牧羊犬", 1);
        Dog dog2 = new Dog("田園犬", 2);
        Dog dog3 = new Dog("哈士奇", 3);
        System.out.println(dog1);
        System.out.println(dog2);
        System.out.println(dog3);
    }
}

舉例2

public class Feature07 {
    @Test
    public void test1(){
        //測試構(gòu)造器
        Person p1 = new Person("羅密歐",new Person("zhuliye",null));
        //測試toString()
        System.out.println(p1);
        //測試equals():
        Person p2 = new Person("羅密歐",new Person("zhuliye",null));
        System.out.println(p1.equals(p2));

        //測試hashCode()和equals()
        HashSet<Person> set = new HashSet<>();
        set.add(p1);
        set.add(p2);

        for (Person person : set) {
            System.out.println(person);
        }

        //測試name()和partner():類似于getName()和getPartner()
        System.out.println(p1.name());
        System.out.println(p1.partner());

    }

    @Test
    public void test2(){
        Person p1 = new Person("zhuyingtai");

        System.out.println(p1.getNameInUpperCase());

        Person.nation = "CHN";
        System.out.println(Person.showNation());

    }
}
public record Person(String name,Person partner) {

    //還可以聲明靜態(tài)的屬性、靜態(tài)的方法、構(gòu)造器、實例方法

    public static String nation;

    public static String showNation(){
        return nation;
    }

    public Person(String name){
        this(name,null);
    }

    public String getNameInUpperCase(){
        return name.toUpperCase();
    }
    //不可以聲明非靜態(tài)的屬性
//    private int id;//報錯
}

//不可以將record定義的類聲明為abstract的
//abstract record Order(){
//
//}

//不可以給record定義的類聲明顯式的父類(非Record類)
//record Order() extends Thread{
//
//}

JDK15中第二次預(yù)覽特性

JDK16中轉(zhuǎn)正特性

最終到JDK16中轉(zhuǎn)正。

記錄不適合哪些場景

record的設(shè)計目標(biāo)是提供一種將數(shù)據(jù)建模為數(shù)據(jù)的好方法。它也不是 JavaBeans 的直接替代品,因為 record的方法不符合 JavaBeans 的 get 標(biāo)準(zhǔn)。另外 JavaBeans 通常是可變的,而記錄是不可變的。盡管它們的用途有點像,但記錄并不會以某種方式取代 JavaBean。

1.8 密封類

背景:

在 Java 中如果想讓一個類不能被繼承和修改,這時我們應(yīng)該使用 final 關(guān)鍵字對類進行修飾。不過這種要么可以繼承,要么不能繼承的機制不夠靈活,有些時候我們可能想讓某個類可以被某些類型繼承,但是又不能隨意繼承,是做不到的。Java 15 嘗試解決這個問題,引入了 sealed 類,被 sealed 修飾的類可以指定子類。這樣這個類就只能被指定的類繼承。

JDK15的預(yù)覽特性:

通過密封的類和接口來限制超類的使用,密封的類和接口限制其它可能繼承或?qū)崿F(xiàn)它們的其它類或接口。

具體使用:

  • 使用修飾符sealed,可以將一個類聲明為密封類。密封的類使用保留關(guān)鍵字permits列出可以直接擴展(即extends)它的類。

  • sealed 修飾的類的機制具有傳遞性,它的子類必須使用指定的關(guān)鍵字進行修飾,且只能是 final、sealednon-sealed 三者之一。

舉例:

public abstract sealed class Shape permits Circle, Rectangle, Square {...}

public final class Circle extends Shape {...} //final表示Circle不能再被繼承了

public sealed class Rectangle extends Shape permits TransparentRectangle, FilledRectangle {...}

public final class TransparentRectangle extends Rectangle {...}

public final class FilledRectangle extends Rectangle {...}

public non-sealed class Square extends Shape {...} //non-sealed表示可以允許任何類繼承

JDK16二次預(yù)覽特性

JDK17中轉(zhuǎn)正特性

2. API的變化

2.1 Optional類

JDK8的新特性

到目前為止,臭名昭著的空指針異常是導(dǎo)致Java應(yīng)用程序失敗的最常見原因。以前,為了解決空指針異常,Google在著名的Guava項目引入了Optional類,通過檢查空值的方式避免空指針異常。受到Google的啟發(fā),Optional類已經(jīng)成為Java 8類庫的一部分。

Optional<T> 類(java.util.Optional) 是一個容器類,它可以保存類型T的值,代表這個值存在。或者僅僅保存null,表示這個值不存在。如果值存在,則isPresent()方法會返回true,調(diào)用get()方法會返回該對象。

Optional提供很多有用的方法,這樣我們就不用顯式進行空值檢測。

  • 創(chuàng)建Optional類對象的方法:

  • static <T> Optional<T> empty() :用來創(chuàng)建一個空的Optional實例

    • static <T> Optional<T> of(T value) :用來創(chuàng)建一個Optional實例,value必須非空
    • static <T> Optional<T> ofNullable(T value) :用來創(chuàng)建一個Optional實例,value可能是空,也可能非空
  • 判斷Optional容器中是否包含對象:

    • boolean isPresent() : 判斷Optional容器中的值是否存在
    • void ifPresent(Consumer<? super T> consumer) :判斷Optional容器中的值是否存在,如果存在,就對它進行Consumer指定的操作,如果不存在就不做
  • 獲取Optional容器的對象:

  • T get(): 如果調(diào)用對象包含值,返回該值。否則拋異常。T get()of(T value)配合使用

  • T orElse(T other) orElse(T other)ofNullable(T value)配合使用,如果Optional容器中非空,就返回所包裝值,如果為空,就用orElse(T other)other指定的默認值(備胎)代替

  • T orElseGet(Supplier<? extends T> other) :如果Optional容器中非空,就返回所包裝值,如果為空,就用Supplier接口的Lambda表達式提供的值代替

  • T orElseThrow(Supplier<? extends X> exceptionSupplier) :如果Optional容器中非空,就返回所包裝值,如果為空,就拋出你指定的異常類型代替原來的NoSuchElementException

舉例:

import java.util.Optional;

import org.junit.Test;

public class TestOptional {
	@Test
    public void test1(){
        String str = "hello";
        Optional<String> opt = Optional.of(str);
        System.out.println(opt);
    }
    @Test
    public void test2(){
        Optional<String> opt = Optional.empty();
        System.out.println(opt);
    }
    @Test
    public void test3(){
        String str = null;
        Optional<String> opt = Optional.ofNullable(str);
        System.out.println(opt);
    }
    @Test
    public void test4(){
        String str = "hello";
        Optional<String> opt = Optional.of(str);

        String string = opt.get();
        System.out.println(string);
    }
    @Test
    public void test5(){
        String str = null;
        Optional<String> opt = Optional.ofNullable(str);
//		System.out.println(opt.get());//java.util.NoSuchElementException: No value present
    }
    @Test
    public void test6(){
        String str = "hello";
        Optional<String> opt = Optional.ofNullable(str);
        String string = opt.orElse("csdn");
        System.out.println(string);
    }
    @Test
    public void test7(){
        String str = null;
        Optional<String> opt = Optional.ofNullable(str);
        String string = opt.orElseGet(String::new);
        System.out.println(string);
    }
    @Test
    public void test8(){
        String str = null;
        Optional<String> opt = Optional.ofNullable(str);
        String string = opt.orElseThrow(()->new RuntimeException("值不存在"));
        System.out.println(string);
    }
    @Test
    public void test9(){
        String str = "Hello1";
        Optional<String> opt = Optional.ofNullable(str);
        //判斷是否是純字母單詞,如果是,轉(zhuǎn)為大寫,否則保持不變
        String result = opt.filter(s->s.matches("[a-zA-Z]+"))
                .map(s -> s.toUpperCase()).orElse(str);
        System.out.println(result);
    }
}

這是JDK9-11的新特性

新增方法 描述 新增的版本
boolean isEmpty() 判斷value是否為空 JDK 11
ifPresentOrElse(Consumer<? super T> action, Runnable emptyAction) value非空,執(zhí)行參數(shù)1功能;如果value為空,執(zhí)行參數(shù)2功能 JDK 9
Optional<T> or(Supplier<? extends Optional<? extends T>> supplier) value非空,返回對應(yīng)的Optional;value為空,返回形參封裝的Optional JDK 9
Stream<T> stream() value非空,返回僅包含此value的Stream;否則,返回一個空的Stream JDK 9
T orElseThrow() value非空,返回value;否則拋異常NoSuchElementException JDK 10

2.2 String存儲結(jié)構(gòu)和API變更

這是JDK9的新特性。

產(chǎn)生背景:

Motivation
The current implementation of the String class stores characters in a char array, using two bytes (sixteen bits) for each character. Data gathered from many different applications indicates that strings are a major component of heap usage and, moreover, that most String objects contain only Latin-1 characters. Such characters require only one byte of storage, hence half of the space in the internal char arrays of such String objects is going unused.

背景
String類的當(dāng)前實現(xiàn)將字符存儲在字符數(shù)組中,每個字符使用兩個字節(jié)(16位)。從許多不同的應(yīng)用程序收集的數(shù)據(jù)表明,字符串是堆使用的主要組成部分,而且,大多數(shù)String對象只包含Latin-1字符。這些字符只需要一個字節(jié)的存儲空間,因此這些String對象的內(nèi)部字符數(shù)組中有一半的空間是未使用的。

使用說明:

Description

We propose to change the internal representation of the String class from a UTF-16 char array to a byte array plus an encoding-flag field. The new String class will store characters encoded either as ISO-8859-1/Latin-1 (one byte per character), or as UTF-16 (two bytes per character), based upon the contents of the string. The encoding flag will indicate which encoding is used.

描述:
我們建議將String類的內(nèi)部表示形式從UTF-16字符數(shù)組更改為字節(jié)數(shù)組加上編碼標(biāo)志字段。新的String類將根據(jù)字符串的內(nèi)容存儲編碼為ISO-8859-1/Latin-1(每個字符一個字節(jié))或UTF-16(每個字符兩個字節(jié))的字符。編碼標(biāo)志將指示使用哪種編碼

結(jié)論:String 再也不用 char[] 來存儲啦,改成了 byte[] 加上編碼標(biāo)記,節(jié)約了一些空間。

public final class String
    implements java.io.Serializable, Comparable<String>, CharSequence {
    @Stable
    private final byte[] value;
	...
}

拓展:StringBufferStringBuilder

那StringBuffer 和 StringBuilder 是否仍無動于衷呢?

String-related classes such as AbstractStringBuilder, StringBuilder, and StringBuffer will be updated to use the same representation, as will the HotSpot VM’s intrinsic string operations.

翻譯
與字符串相關(guān)的類,如AbstractStringBuilder、StringBuilder和StringBuffer,將被更新為使用相同的表示,HotSpot VM的固有字符串操作也是如此。

JDK11新特性:新增了一系列字符串處理方法

描述 舉例
判斷字符串是否為空白 " ".isBlank(); // true
去除首尾空白 " Javastack ".strip(); // “Javastack”
去除尾部空格 " Javastack ".stripTrailing(); // " Javastack"
去除首部空格 " Javastack ".stripLeading(); // "Javastack "
復(fù)制字符串 "Java".repeat(3);// “JavaJavaJava”
行數(shù)統(tǒng)計 "A\nB\nC".lines().count(); // 3

JDK12新特性:String 實現(xiàn)了 Constable 接口

String源碼:

public final class String implements java.io.Serializable, Comparable<String>, CharSequence,Constable, ConstantDesc {

java.lang.constant.Constable接口定義了抽象方法:

public interface Constable {
	Optional<? extends ConstantDesc> describeConstable();
}

Java 12 String 的實現(xiàn)源碼:

/**
 * Returns an {@link Optional} containing the nominal descriptor for this
 * instance, which is the instance itself.
 *
 * @return an {@link Optional} describing the {@linkplain String} instance
 * @since 12
 */
@Override
public Optional<String> describeConstable() {
	return Optional.of(this);
}

很簡單,其實就是調(diào)用 Optional.of 方法返回一個 Optional 類型。

舉例:

private static void testDescribeConstable() {
	String name = "Java高級工程師";
	Optional<String> optional = name.describeConstable();
	System.out.println(optional.get());
}

結(jié)果輸出:

Java高級工程師

JDK12新特性:String新增方法

String的transform(Function)

var result = "foo".transform(input -> input + " bar");
System.out.println(result); //foo bar

或者

var result = "foo".transform(input -> input + " bar").transform(String::toUpperCase)
System.out.println(result); //FOO BAR

對應(yīng)的源碼:

/**
* This method allows the application of a function to {@code this}
* string. The function should expect a single String argument
* and produce an {@code R} result.
* @since 12
*/
public <R> R transform(Function<? super String, ? extends R> f) {
 return f.apply(this);
}

在某種情況下,該方法應(yīng)該被稱為map()。

舉例:

private static void testTransform() {
	System.out.println("======test java 12 transform======");
	List<String> list1 = List.of("Java", " Python", " C++ ");
	List<String> list2 = new ArrayList<>();
	list1.forEach(element -> list2.add(element.transform(String::strip)
								  .transform(String::toUpperCase)
								  .transform((e) -> "Hi," + e))
				 );
	list2.forEach(System.out::println);
}

結(jié)果輸出:

======test java 12 transform======
Hi,JAVA
Hi,PYTHON
Hi,C++

如果使用Java 8的Stream特性,可以如下實現(xiàn):

private static void testTransform1() {
        System.out.println("======test before java 12 ======");
        List<String> list1 = List.of("Java  ", " Python", " C++ ");

        Stream<String> stringStream = list1.stream().map(element -> element.strip()).map(String::toUpperCase).map(element -> "Hello," + element);
        List<String> list2 = stringStream.collect(Collectors.toList());
        list2.forEach(System.out::println);
    }

2.3 JDK17:標(biāo)記刪除Applet API

Applet API 提供了一種將 Java AWT/Swing 控件嵌入到瀏覽器網(wǎng)頁中的方法。不過,目前 Applet 已經(jīng)被淘汰。大部分人可能壓根就沒有用過 Applet。

Applet API 實際上是無用的,因為所有 Web 瀏覽器供應(yīng)商都已刪除或透露計劃放棄對 Java 瀏覽器插件的支持。Java 9 的時候,Applet API 已經(jīng)被標(biāo)記為過時,Java 17 的時候終于標(biāo)記為刪除了。

具體如下:

java.applet.Applet
java.applet.AppletStub
java.applet.AppletContext
java.applet.AudioClip
javax.swing.JApplet
java.beans.AppletInitializer

3. 其它結(jié)構(gòu)變化

3.1 JDK9:UnderScore(下劃線)使用的限制

在java 8 中,標(biāo)識符可以獨立使用“_”來命名:

String _ = "hello";
System.out.println(_);

但是,在java 9 中規(guī)定“_”不再可以單獨命名標(biāo)識符了,如果使用,會報錯:

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

3.2 JDK11:更簡化的編譯運行程序

看下面的代碼。

// 編譯
javac JavaStack.java

// 運行
java JavaStack

我們的認知里,要運行一個 Java 源代碼必須先編譯,再運行。而在 Java 11 版本中,通過一個 java 命令就直接搞定了,如下所示:

java JavaStack.java

注意點:

  • 執(zhí)行源文件中的第一個類,第一個類必須包含主方法。

3.3 GC方面新特性

GC是Java主要優(yōu)勢之一。 然而,當(dāng)GC停頓太長,就會開始影響應(yīng)用的響應(yīng)時間。隨著現(xiàn)代系統(tǒng)中內(nèi)存不斷增長,用戶和程序員希望JVM能夠以高效的方式充分利用這些內(nèi)存, 并且無需長時間的GC暫停時間。

3.3.1 G1 GC

JDK9以后默認的垃圾回收器是 G1GC。

JDK10 : 為G1提供并行的 Full GC

G1最大的亮點就是可以盡量的避免full gc。但畢竟是“盡量”,在有些情況下,G1就要進行full gc了,比如如果它無法足夠快的回收內(nèi)存的時候,它就會強制停止所有的應(yīng)用線程然后清理。

在Java10之前,一個單線程版的標(biāo)記-清除-壓縮算法被用于full gc。為了盡量減少full gc帶來的影響,在Java10中,就把之前的那個單線程版的標(biāo)記-清除-壓縮的full gc算法改成了 支持多個線程 同時full gc。這樣也算是減少了full gc所帶來的停頓,從而提高性能。

可以通過-XX:ParallelGCThreads參數(shù)來指定用于并行GC的線程數(shù)。

JDK12:可中斷的 G1 Mixed GC

JDK12:增強G1,自動返回未用堆內(nèi)存給操作系統(tǒng)

3.3.2 Shenandoah GC

JDK12:Shenandoah GC:低停頓時間的GC

Shenandoah 垃圾回收器是 Red Hat 在 2014 年宣布進行的一項垃圾收集器研究項目 Pauseless GC 的實現(xiàn),旨在針對 JVM 上的內(nèi)存收回實現(xiàn)低停頓的需求。

據(jù) Red Hat 研發(fā) Shenandoah 團隊對外宣稱,Shenandoah 垃圾回收器的暫停時間與堆大小無關(guān),這意味著無論將堆設(shè)置為 200 MB 還是 200 GB,都將擁有一致的系統(tǒng)暫停時間,不過實際使用性能將取決于實際工作堆的大小和工作負載。

Shenandoah GC 主要目標(biāo)是 99.9% 的暫停小于 10ms,暫停與堆大小無關(guān) 等。

這是一個實驗性功能,不包含在默認(Oracle)的OpenJDK版本中。

Shenandoah開發(fā)團隊在實際應(yīng)用中的測試數(shù)據(jù):

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

JDK15:Shenandoah垃圾回收算法轉(zhuǎn)正

Shenandoah垃圾回收算法終于從實驗特性轉(zhuǎn)變?yōu)楫a(chǎn)品特性,這是一個從 JDK 12 引入的回收算法,該算法通過與正在運行的 Java 線程同時進行疏散工作來減少 GC 暫停時間。Shenandoah 的暫停時間與堆大小無關(guān),無論堆棧是 200 MB 還是 200 GB,都具有相同的一致暫停時間。

Shenandoah在JDK12被作為experimental引入,在JDK15變?yōu)?code>Production;之前需要通過-XX:+UnlockExperimentalVMOptions -XX:+UseShenandoahGC來啟用,現(xiàn)在只需要-XX:+UseShenandoahGC即可啟用

3.3.3 革命性的 ZGC

JDK11:引入革命性的 ZGC

ZGC,這應(yīng)該是JDK11最為矚目的特性,沒有之一。

ZGC是一個并發(fā)、基于region、壓縮型的垃圾收集器

ZGC的設(shè)計目標(biāo)是:支持TB級內(nèi)存容量,暫停時間低(<10ms),對整個程序吞吐量的影響小于15%。 將來還可以擴展實現(xiàn)機制,以支持不少令人興奮的功能,例如多層堆(即熱對象置于DRAM和冷對象置于NVMe閃存),或壓縮堆。

JDK13:ZGC:將未使用的堆內(nèi)存歸還給操作系統(tǒng)

JDK14:ZGC on macOS和windows

  • JDK14之前,ZGC僅Linux才支持?,F(xiàn)在mac或Windows上也能使用ZGC了,示例如下:

    -XX:+UnlockExperimentalVMOptions -XX:+UseZGC
    
  • ZGC與Shenandoah目標(biāo)高度相似,在盡可能對吞吐量影響不大的前提下,實現(xiàn)在任意堆內(nèi)存大小下都可以把垃圾收集的停頓時間限制在十毫秒以內(nèi)的低延遲。

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)

JDK15:ZGC 功能轉(zhuǎn)正

ZGC是Java 11引入的新的垃圾收集器,經(jīng)過了多個實驗階段,自此終于成為正式特性。

但是這并不是替換默認的GC,默認的GC仍然還是G1;之前需要通過-XX:+UnlockExperimentalVMOptions、 -XX:+UseZGC來啟用ZGC,現(xiàn)在只需要-XX:+UseZGC就可以。相信不久的將來它必將成為默認的垃圾回收器。

ZGC的性能已經(jīng)相當(dāng)亮眼,用“令人震驚、革命性”來形容,不為過。未來將成為服務(wù)端、大內(nèi)存、低延遲應(yīng)用的首選垃圾收集器。

怎么形容Shenandoah和ZGC的關(guān)系呢?異同點大概如下:

  • 相同點:性能幾乎可認為是相同的
  • 不同點:ZGC是Oracle JDK的,根正苗紅。而Shenandoah只存在于OpenJDK中,因此使用時需注意你的JDK版本

JDK16:ZGC 并發(fā)線程處理

在線程的堆棧處理過程中,總有一個制約因素就是safepoints。在safepoints這個點,Java的線程是要暫停執(zhí)行的,從而限制了GC的效率。

回顧:

我們都知道,在之前,需要 GC 的時候,為了進行垃圾回收,需要所有的線程都暫停下來,這個暫停的時間我們稱為 Stop The World。

而為了實現(xiàn) STW 這個操作, JVM 需要為每個線程選擇一個點停止運行,這個點就叫做安全點(Safepoints)。

ZGC的并發(fā)線程堆棧處理可以保證Java線程可以在GC safepoints的同時可以并發(fā)執(zhí)行。它有助于提高所開發(fā)的Java軟件應(yīng)用程序的性能和效率。

4. 小結(jié)與展望

隨著云計算和 AI 等技術(shù)浪潮,當(dāng)前的計算模式和場景正在發(fā)生翻天覆地的變化,不僅對 Java 的發(fā)展速度提出了更高要求,也深刻影響著 Java 技術(shù)的發(fā)展方向。傳統(tǒng)的大型企業(yè)或互聯(lián)網(wǎng)應(yīng)用,正在被云端、容器化應(yīng)用、模塊化的微服務(wù)甚至是函數(shù)(FaaS, Function-as-a-Service)所替代。

Java 需要在新的計算場景下,改進開發(fā)效率。 比如,Java 代碼雖然進行了一些類型推斷等改進,更易用的集合 API 等,但仍然給開發(fā)者留下了過于刻板、形式主義的印象,這是一個長期的改進方向。

Java雖然標(biāo)榜面向?qū)ο缶幊?,卻毫不顧忌的加入面向接口編程思想,又扯出匿名對象的概念,每增加一個新的東西,對Java的根本(面向?qū)ο笏枷耄┑囊淮螞_擊。文章來源地址http://www.zghlxwxcb.cn/news/detail-463371.html

到了這里,關(guān)于JDK8-JDK17中的新特性(var類型推斷、模式匹配、Record、密封類)的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務(wù),不擁有所有權(quán),不承擔(dān)相關(guān)法律責(zé)任。如若轉(zhuǎn)載,請注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實不符,請點擊違法舉報進行投訴反饋,一經(jīng)查實,立即刪除!

領(lǐng)支付寶紅包贊助服務(wù)器費用

相關(guān)文章

  • JDK8,JDK11,JDK17,JDK21及中間版本主要更新特性

    JDK8,JDK11,JDK17,JDK21及中間版本主要更新特性

    官方地址: https://www.oracle.com/java/technologies/java-se-support-roadmap.html 從上圖可以很清晰得可以看出,JDK7,JDK8,JDK11,JDK17,JDK21是長期維護的版本。從目前來看,JDK8到2023年已經(jīng)有將近10年的歷史了,大多數(shù)依據(jù)JDK8的相關(guān)技術(shù)內(nèi)容已經(jīng)很成熟了,但是大家也看到,JDK在不斷地迭代,JD

    2024年02月21日
    瀏覽(24)
  • JDK8、JDK11、JDK17和JDK21這幾個版本更新的主要特性

    JDK8、JDK11、JDK17和JDK21這幾個版本更新的主要特性

    JDK8 是 Java 的一個重大更新版本,引入了一系列新特性和改進,主要包括: Lambda 表達式: Lambda 表達式允許我們以簡潔、函數(shù)式的方式編寫代碼,使代碼更易于理解和維護。- Stream API : Stream API 提供了一套聲明式處理數(shù)據(jù)的方式,使得對集合和數(shù)組的操作更加直觀和高效。

    2024年04月29日
    瀏覽(23)
  • JDK17新特性之--JDK9到JDK17 String 新增的新方法

    JDK17新特性之--JDK9到JDK17 String 新增的新方法

    JDK9之后對String底層存儲數(shù)據(jù)結(jié)構(gòu)進行了重大的修改 1 ,同步也增加了許多新的方法,主要有Text Blocks、chars()、codePoints()、describeConstable()、formatted()、indent()、isBlank()、isEmpty()、lines()、repeat()、strip()、stripLeading()、stripIndent()、stripTrailing()、translateEscapes(),接下來就逐一看看每個

    2024年02月04日
    瀏覽(23)
  • Windows安裝JDK8-jdk1.8.0_202步驟記錄

    Windows安裝JDK8-jdk1.8.0_202步驟記錄

    后面開始慢慢把技術(shù)重心從web漏洞挖掘轉(zhuǎn)到內(nèi)網(wǎng)滲透了,準(zhǔn)備琢磨琢磨內(nèi)網(wǎng)的一些奇奇怪怪的東西。雖然我一直都有學(xué)習(xí)內(nèi)網(wǎng)滲透,但是由于工作原因,很容易忘記,所以今天就當(dāng)是一個筆記,方便自己回來看看。內(nèi)網(wǎng)肯定不能少cobalt strike,這東西要有java環(huán)境,所以搭了個

    2024年02月04日
    瀏覽(25)
  • IDEA顯示val,var的推斷類型的設(shè)置

    IDEA顯示val,var的推斷類型的設(shè)置

    在java中val,var可以減少繁瑣的代碼量,但是IDEA默認關(guān)掉自動類型,導(dǎo)致使用val,var表示的不能一言判別類型,并且不能顯示點入查看類型的詳情因此需要在idea中設(shè)置,能夠自動顯示推斷類型。 步驟1 Setting---editor---inlay hints ??????????????????????????????????

    2024年02月09日
    瀏覽(77)
  • JDK8新特性

    是 Java 8 引入的一種處理集合數(shù)據(jù)的新方式。它提供了一種更簡潔、更易讀和更靈活的方式來操作和處理集合數(shù)據(jù)。流的核心思想是將數(shù)據(jù)處理操作集中在一起,可以進行過濾、映射、排序、聚合等一系列操作,而不需要顯式地使用循環(huán)和條件語句。 以下是流(Stream)API 的一

    2024年02月15日
    瀏覽(20)
  • JDK8新特性-上部

    JDK8新特性-上部

    ??博客x主頁:己不由心王道長??! ??文章說明:JDK8新特性?? ?系列專欄:Java基礎(chǔ) ??本篇內(nèi)容:對JDK8的新特性進行學(xué)習(xí)和講解?? ??每日一語:這個世界本來就不完美,如果我們再不接受不完美的自己,那我們要怎么活。?? ?? 交流社區(qū): 己不由心王道長(優(yōu)質(zhì)編程

    2024年02月11日
    瀏覽(22)
  • Mac卸載jdk8,安裝jdk17

    Mac卸載jdk8,安裝jdk17

    本次操作基于MacBook 因為工作需要,需要將jdk版本由jdk8升級到j(luò)dk17,同一臺機器上是可以同時安裝多個版本的jdk的,但是為了避免一些沖突和未知問題,這里直接卸載舊版本jdk,然后再重新安裝新版本。 先查看本機安裝的jdk: 刪除java運行環(huán)境: 到j(luò)ava的目錄,用ls命令查看機

    2024年02月08日
    瀏覽(27)
  • JDK8新特性之方法引用【 ::】

    JDK8新特性之方法引用【 ::】

    接下來看看由輝輝所寫的關(guān)于方法引用的相關(guān)操作吧 目錄 ????Welcome Huihui\\\'s Code World ! !???? 一.是什么 二.為什么要用 三.什么時候用 四.怎么用 常見的引用方式 ?符號表示: “ ::” 是一種引用運算符,它所在的表達式稱為方法引用? 1.簡化代碼 方法引用可以將復(fù)雜的代

    2024年02月11日
    瀏覽(47)
  • java jdk8和jdk17同時存在【環(huán)境配置】

    java jdk8和jdk17同時存在【環(huán)境配置】

    jdk8:https://www.oracle.com/cn/java/technologies/javase/javase8u211-later-archive-downloads.html jdk17:https://www.oracle.com/java/technologies/javase/jdk17-archive-downloads.html PS:jdk8在下載結(jié)束,安裝的時候,需要有兩個文件分別是jre和jdk JRE: 是Java Runtime Environment,是java程序的運行環(huán)境。既然是運行,當(dāng)然要包含

    2024年02月07日
    瀏覽(31)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包