1. 程式人生 > 實用技巧 >String類

String類

案例1String儲存位置介紹:

package com.javaSe.String;
/*


重要的資訊,在JDK7的時候,就把字串常量池移動到了堆記憶體當中了,現在不在方法區了。


關於java JDK中內建的一個類:java.lang.String
    1 String表示字串型別,屬於引用資料型別,不屬於基本資料型別。
    2 在java中隨便使用雙引號括起來的都是String例如:"abc" "123" "12.3" 這是3個String物件
    3 java中規定,雙引號括起來的字串,是不可變得,也就是說"abc",自出生到死亡,不可變,不能變成"abcd"也不能變成"ab"。
    4 在JDK當中雙括號括起來的字串,例如:"abc" "123"都是直接儲存在“方法區”的字串“常量池”當中的。
        為什麼SUN公司把字串儲存在一個字串常量池當中呢。因為字串在實際的開發中使用的太頻繁。為了執行效率。
        所以把字串放到了方法區的字串常量池當中。
*/ public class StringTest01 { public static void main(String[] args) { // 以下兩行程式碼是在字串常量池當中建立了3個字串物件。都在字串常量池當中。 String s1 = "abc"; String s2 = "abc" + "def"; // 分析:這是使用new的方式建立的字串物件。這個程式碼中的"xy"是從哪裡來的? // 凡是雙引號括起來的都在字串常量池中有一份 // new物件的時候一定在堆記憶體中開闢空間 String s3 = new
String("xy"); } }

記憶體圖:

案例使用者類:

package com.javaSe.String;


public class User {
    private int id;
    private String name;
    
    public User() {
    }
    
    public User(int id, String name) {
        this.id = id; 
        this.name = name;
    }
    
    public int getId() {
        
return id; } public void setId(int id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } }

使用者測試類:

package com.javaSe.String;


public class UsetTest {
    public static void main(String[] args) {
        User user = new User(111,"張三");
    }
}

記憶體圖:

String案例2String s = "" 和 String s1 = new String("")的區別:
package com.javaSe.String;


public class StringTest02 {
    public static void main(String[] args) {
        String s1 = "hello";
        // "hello"是儲存在方法區的字串常量池當中
        // 所以這個"hello"不會新建(因為這個物件已經存在了。)
        String s2 = "hello";
        // 分析結果是true還是false?
        // == 雙等號比較的是不是變數中儲存的記憶體地址?是的。
        System.out.println(s1 == s2);//true
        
        String x = new String("xyz");
        String y = new String("xyz");
        // 分析結果是true還是false?
        // == 雙等號比較的是不是變數中儲存的記憶體地址?是的。
        System.out.println(x == y);//false
        
        // 通過這個案例的學習,我們知道了,字串物件之間的比較不能使用“==”
        // “==”不保險,應該呼叫String類的equals方法。
        // String類已經重寫了equals方法,以下的equals方法呼叫的是重寫之後的equals方法。
        System.out.println(x.equals(y));// true
        
        String k = new String("testString");
        // "testString"這個字串可以後面加"."呢?
        // 因為"testString"是一個String字串物件。只要是物件都能呼叫方法。
        System.out.println("testString".equals(k));// 建議使用這種方式,因為這個可以避免空指標異常。
        System.out.println(k.equals("testString"));// 存在空指標異常的風險,不建議這樣寫。
    }
}

String案例3 當你使用new String("")建立物件的時候 堆記憶體中會有幾個物件:

package com.javaSe.String;


public class StringTest03 {
    public static void main(String[] args) {
        /*
        一共3個物件:
            方法區字串常量池中有1一個:“hello”
            堆記憶體中有兩個String物件。
            一共3個
        */
        String s1 = new String("hello");
        String s2 = new String("hello");
    }
}

String案例4將byte陣列轉換成字串:

package com.javaSe.String;


public class StringTest04 {
    public static void main(String[] args) {
        
        // 建立字串物件最常用的一種方式
        String s1 = "hello world!";
        
        // s1這個變數中儲存的是一個記憶體地址。
        // 按說以下應該輸出一個地址
        // 但是輸出一個字串,說明String類已經重寫了toString()方法。
        System.out.println(s1);//hello world!
        
        
        // 這裡只掌握常用的構造方法。
        byte[] bytes = {97,98,99};// 97是a,98是b,99是c
        String s2 = new String(bytes);
        // 前面說過:輸出一個引用的時候,會自動呼叫toString()方法,預設Object的話會自動輸出物件的記憶體地址。
        // 通過輸出結果我們得出一個結論:String類已經重寫了toString()方法。
        // 輸出字串物件的話,輸出的不是物件的記憶體地址,而是字串本身。
        System.out.println(s2);
        
        // String(位元組陣列,陣列元素下標的起始位置,長度)
        // 將byte陣列中的一部分轉換成字串。
        String s3 = new String(bytes,1,2);
        System.out.println(s3);// bc
        
        // 將char陣列全部轉換成字串
        // 將char陣列的一部分轉換成字串
        
    }
}

String案例5:String類中的常用方法:

package com.javaSe.String;


import java.sql.SQLOutput;


public class StringTest05 {
    public static void main(String[] args){
        // String類當中常用方法
        // 1 char charAt(int index)
        char c = "中國人".charAt(1);// "中國人"是一個字串String物件。只要是物件就能“.”
        System.out.println(c);//// 2 (瞭解).int compareTo(String anotherString)
        // 字串之間比較大小不能直接使用 > <,需要使用compareTo(String string)方法。
        int result = "abc".compareTo("abc");
        System.out.println(result);// 0 (等於0) 前後一致 10 - 10 = 0
        
        int result2 = "abcd".compareTo("abce");
        System.out.println(result2);// -1(小於0) 前小後大 8 - 9 = -1
        
        int result3 = "abce".compareTo("abcd");
        System.out.println(result3);// 1(大於0) 先大後小 9 - 8 = 1
        
        // 拿著字串第一個字母和後面字串的第一個字母比較。能分勝負就不再比較了。
        System.out.println("xyz".compareTo("yxz")); //-1
        
        // 3 (掌握).boolean contains(CharSequence s)
        // 判斷前面的字串中是否包含後面的字串。
        System.out.println("HelloWorld.java".contains(".java"));// true
        System.out.println("http://www.baidu.com".contains("https://"));// false
        
        // 4 (掌握) .boolean endsWith(String suffix)
        // 判斷當前字串是否以某個子字串結尾。
        System.out.println("test.txt".endsWith(".java"));// false
        System.out.println("test.txt".endsWith(".txt"));// true
        System.out.println("sdfhkshfsdkhfksdh".endsWith("dh"));// true
        
        // 5 (掌握) .boolean equals(Object anObject)
        // 比較兩個字串必須使用equals()方法,不能使用"=="
        // equals()方法有沒有呼叫compareTo()方法?老版本可以看一下。JDK13中並沒有呼叫compareTo()方法。
        // equals只能看出兩個字串之間是否相不相等
        // compareTo方法可以看出是否相等,並且同時還可以判斷誰大誰小。
        System.out.println("abc".equals("abc"));// true
        
        // 6(掌握) .boolean equalsIgnoreCase(String anotherString)
        // 判斷兩個字串是否相等,並且忽略大小寫。
        System.out.println("AbC".equalsIgnoreCase("abc"));//true
        
        // 7 (掌握) byte[] getBytes()
        // 將字串物件轉換成位元組陣列
        byte[] b = "abcdef".getBytes();
        for(int i = 0; i < b.length ; i++){
            System.out.println(b[i]);
        }
        
        // 8 (掌握) int indexOf(String str)
        // 判斷某個子字串在當前字串中第一次出現的地方的索引(下標)。
        System.out.println("orcalejavac++.netc#phppythonjavaorcalec++".indexOf("java")); // 6
        
        // 9 (掌握) boolean isEmpty()
        // 判斷某個字串是否為空的字串 底層原始碼呼叫的應該是字串的length()方法。
        // 不是null哦  null的話會引起空指標異常哦
        String s = "";
        System.out.println(s.isEmpty());// true
        
        // 10(掌握) int length()
        // 面試題:判斷陣列長度和判斷字串長度不一樣。
        // 判斷陣列長度是length屬性。判斷字串長度是length()方法。
        System.out.println("abc".length());// 3
        
        System.out.println("".length());// 0
        
        // 11(掌握) int lastIndexOf(String str)
        // 判斷某個子字串在當前字串中最後一次出現的索引(下標)
        System.out.println("orcalejavac++javac#phpjavapython".lastIndexOf("java")); // 22
        
        // 12(掌握) String replace(CharSequence target, CharSequence replacement)
        // 替換的意思。
        // String的父介面就是:CharSequence
        System.out.println("http://www.baidu.com".replace("http://","https://")); // https://www.baidu.com
        // 把以下字串中的“=”替換成“:”
        System.out.println("name=zhangsan&passworld=123&age=20".replace("=",":"));//name:zhangsan&passworld:123&age:20
        
        // 13(掌握) String[] split(String regex)
        // 拆分字串
        String[] ymd = "1980-10-11".split("-");// "1980-10-11"以"-"分隔符進行拆分。
        for (int i = 0; i < ymd.length; i++) {
            System.out.println(ymd[i]);
        }
        
        String param = "name=zhangsan&passworld=123&age=20";
        String[] params = param.split("&");
        for (int i = 0; i < params.length; i++) {
            System.out.println(params[i]);
            // 可以繼續向下拆分,可以通過"="進行拆分
            String[] s1 = params[i].split("=");
            for (int j = 0; j < s1.length; j++) {
                System.out.println(s1[j]);
            }
        }
        
        // 14(掌握) boolean startsWith(String prefix)
        // 判斷某個字串是否以某個子字串開始
        System.out.println("http://www.baidu.com".startsWith("http"));//true
        System.out.println("http://www.baidu.com".startsWith("https"));//false
        
        // 15(掌握) String substring(int beginIndex) 引數是起始下標
        // 擷取字串
        System.out.println("http://www.baidu.com".substring(7)); // www.baidu.com
        
        // 16(掌握)  String substring(int beginIndex, int endIndex)
        // 從第一個下標開始  以endIndex - 1處停止。
        // beginIndex起始位置(包括)
        // endIndex結束位置(不包括)
        System.out.println("http://www.baidu.com".substring(7,10));// www
        
        // 17(掌握)char[] toCharArray()
        // 將字串轉換成char陣列
        char[] chars = "我是中國人".toCharArray();
        for (int i = 0; i < chars.length; i++) {
            System.out.println(chars[i]);
        }
        
        // 18(掌握) String toLowerCase()
        // 轉換為小寫
        System.out.println("ABFDJKFH".toLowerCase()); // abfdjkfh
        
        // 19(掌握) String toUpperCase()
        System.out.println("abfdjkfh".toUpperCase()); // ABFDJKFH
        
        // 20(掌握) String trim();
        // 去除字串前後空白  中間的空白不會去除
        System.out.println("           Hello   World               ".trim()); // Hello   World
        
        // 21(掌握) String中只有一個方法是靜態的,不需要new物件
        // 這個方法叫做valueOf
        // 作用:將“非字串”轉換成“字串”
        // String s1 = String.valueOf(true); // "true"
        String s1 = String.valueOf(100); // "100"
        System.out.println(s1);
        
        // 這個靜態的valueOf()方法,引數是一個物件的時候,會自動呼叫該物件的toString()方法嗎?
        String s2 = String.valueOf(new Customer());
        // System.out.println(s2); // 沒有重寫toString()方法之前是物件記憶體地址  "com.javaSe.String.Customer@10f87f48"
        System.out.println(s2); // 我是一個VIP客戶!!!
        
        // 我們是不是可以研究一下println()方法的原始碼了?
        System.out.println(100);
        System.out.println(3.14);
        System.out.println(true);
        // 通過原始碼可以看出:為什麼輸出一個引用的時候,會呼叫toString()方法!!!!
        // 本質上System.out.println()這個方法在輸出任何資料的時候都是先轉換成字串,在輸出。
        System.out.println(new Object());
    
        System.out.println(new Customer());
    }
}


class Customer{
    // 重寫toString()方法
    
    @Override
    public String toString() {
        return "我是一個VIP客戶!!!";
    }
}