# 字符串

  • String是Java定义好的一个类。定义在Java.lang包中,所以使用的时候不需要导包.
  • Java中的所有字符串文字,都可以使用此类进行定义
  • 字符串不可变,他们的值在创建后不能被修改

# 使用直接复制的方式,获取一个字符串对象

public class main {
    public static void main(String[] args) {
        String str = "Hello World";
        System.out.println(str);
    }
}

# 使用new的方式来获取一个字符串对象

注意

使用new关键字创建的字符串对象是一个对象属于引用数据类型

   public class main {
    public void main(String[] args) {
        String str1 = new String("Hello World");
        String str2 = "Hello World";
        System.out.println(str1 == str2);//false
    }
}
public class main {
    public static void main(String[] args) {
        //空参构造
        String str1 = new String();//""


        //有参构造

        //传递字符串
        String str2 = new String("Hello World");
        System.out.println(str2);//Hello World

        //传递字符数组
        char[] chars = {'H', 'e', 'l', 'l', 'o', ' ', 'W', 'o', 'r', 'l', 'd'};
        String str3 = new String(chars);
        System.out.println(str3);//Hello World

        //传递字节数组
        //会将字节转换为ascii码
        //应用场景 网络当中传输的数据其实都是字节信息
        //一般使用字节信息转换为字符串

        byte[] bytes = {97, 98, 99, 100, 101, 102, 103, 104, 105, 106};
        String str5 = new String(bytes);
        System.out.println(str5);//abcdefghij
    }
}

# 字符串比较

# 使用==号比较

  • 基本数据类型比较的是字符串值
  • 引用数据类型比较的是地址值
public class main {
    public void main(String[], args) {
        //创建两个字符串对象
        String str1 = new String("Hello World");
        String str2 = "Hello World";
        System.out.println(str1 == str2);//false
    }
}

# 使用字符串中的equals方法比较

  • equals方法比较的是字符串值

public class main {
    public void main(String[], args) {
//创建两个字符串对象
        String str1 = new String("Hello World");
        String str2 = "Hello World";
        System.out.println(str1.equals(str2));//true
    }
}

# 使用equalsIgnoreCase方法比较 (忽略大小写)

  • equalsIgnoreCase方法比较的是字符串值,忽略大小写
  • 忽略大小写只能是英文状态下,A,a
public class main {
    public void main(String[], args) {
        String str1 = new String("Hello World");
        String str2 = "hello world";
        System.out.println(str1.equalsIgnoreCase(str2));//true
    }
}

# 遍历字符串

  • 遍历字符串,就是遍历字符串中的每一个字符
  • 使用string中的length方法获取字符串的长度

    注意

    string中的length是一个方法,而数组中的length是一个属性

  • 使用str.charAt(index)获取字符串中指定位置的字符
public class main {
    public void main(String[], args) {
        String str = "Hello World";
        for (int i = 0; i < str.length(); i++)
            System.out.println(str.charAt(i));
    }
}

# 截取字符串

  • 使用str.substring(start,end)截取字符串
  • start表示截取的起始位置,end表示截取的结束位置,但不包含end位置的字符
public class main {
    public void main(String[], args) {
        String str = "Hello World";
        System.out.println(str.substring(0, 5));//Hello
    }
}

# 字符串替换

使用字符串的replace(oldChar,newChar)方法替换字符串中的字符

  • oldChar表示要替换的字符
  • newChar表示替换后的字符
public class main {
    public void main(String[], args) {
        String str = "Hello World";
        System.out.println(str.replace('l', 'L'));//HeLlo WorLd
    }
}

# 字符串练习

# 将数字转化为大写

  • 将阿拉伯数字转为中文大写
  • 要求加入单位
  • 固定七位
  • 78909 转为 零佰零拾柒万捌仟玖佰零拾玖元
public class main {
    public void main(String[] args) {
        //将数字转大写
        //数字大写数组
        String[] strMax = {"零", "壹", "贰", "叁", "肆", "伍", "陆", "柒", "捌", "玖"};
        //单位数组
        String[] strUnit = {"佰", "拾", "万", "仟", "佰", "拾", "元"};
        int num = 78909;
        //数字强制类型转换
        String numToString = String.valueOf(num);
        //将现有数字变为大写
        StringBuilder numToStringMax = new StringBuilder();
        for (int i = 0; i < numToString.length(); i++)
            numToStringMax.append(strMax[numToString.charAt(i) - '0']);

        //不足七位前面补零
        while (numToStringMax.length() < 7)
            numToStringMax.insert(0, "零");

        System.out.println(numToStringMax);

        //插入单位
        StringBuilder result = new StringBuilder();
        for (int i = 0; i < strUnit.length; i++)
            result.append(numToStringMax.charAt(i)).append(strUnit[i]);

        System.out.println(result);
    }
}

# 字符串StringBuilder

注意

StringBuilder类不适用于多线程的情况,有线程安全问题,如果项目存在多线程建议使用StringBuffer

  • StringBuilder类可以看做一个容器,创建之后里面的内容是可变的
  • 作用:提高字符串的操作效率
  • 在使用字符串进行拼接操作时,因为字符串是不可变的,所以每次拼接都会创建一个新的字符串,这样会消耗大量的内存。

# 构造方法

方法名 说明
public StringBuilder() 创建一个空白的可变字符串StringBuilder对象
public StringBuilder(String str) 根据字符串的内容,创建可变字符串StringBuilder对象

# 成员方法

方法名 说明
public StringBuilder append(String str)(任意类型) 将指定的字符串追加到当前字符串的末尾
public StringBuilder reverse() 反转容器中的内容
public StringBuilder insert(int offset,String str)(任意类型) 将指定的字符串插入到当前字符串的指定位置
public StringBuilder delete(int start,int end) 删除从start开始到end结束的子串
public StringBuilder replace(int start,int end,String str)(任意类型) 用指定的字符串替换当前字符串中从start开始到end结束的子串
public int lastIndexOf(String str) 返回指定子字符串在此字符串中最后一次出现处的索引
public int indexOf(String str) 返回指定子字符串在此字符串中第一次出现处的索引
public int length() 返回容器中字符串的长度
public String toString() 将当前StringBuilder对象转换为String对象
public class main {
    public void main(String[], args) {
        //字符串StringBuilder类相关
        //append方法 将指定的字符串追加到当前字符串的末尾
        StringBuilder str = new StringBuilder("Hello World");
        str.append("Java");//Hello WorldJava

        //reverse方法
        StringBuilder str1 = new StringBuilder("Hello World");
        str1.reverse();
        System.out.println(str1);//dlroW olleH

        //insert方法  将指定的字符串插入到当前字符串的指定位置
        StringBuilder str2 = new StringBuilder("Hello World");
        str2.insert(5, "Java");
        System.out.println(str2);//HelloJava World

        //delete方法 删除当前字符串的指定位置的子字符串
        StringBuilder str3 = new StringBuilder("Hello World");
        str3.delete(5, 10);
        System.out.println(str3);//Hellod

        //replace方法 替换当前字符串的指定位置的子字符串
        StringBuilder str4 = new StringBuilder("Hello World");
        str4.replace(5, 10, "Java");
        System.out.println(str4);//HelloJavad

        //lastIndexOf方法 返回指定子字符串在此字符串中最后一次出现处的索引
        String str5 = "Hello World";
        System.out.println(str5.lastIndexOf("l"));//9

        //indexOf方法 返回指定子字符串在此字符串中第一次出现处的索引
        String str6 = "Hello World";
        System.out.println(str6.indexOf("l"));//2

        //length方法 返回字符串的长度
        String str7 = "Hello World";
        System.out.println(str7.length());//11

        //toString方法 将当前字符串对象转换为字符串
        StringBuilder str8 = new StringBuilder("Hello World");
        System.out.println(str8.toString());//Hello World
    }
}

# 字符串StringJoiner

  • StringJoiner类是jdk1.8之后出现的,作用是拼接字符串,比StringBuilder类性能更高

# 构造方法

方法名 说明
public StringJoiner(String delimiter) 根据指定的分隔符创建StringJoiner对象
public StringJoiner(String delimiter,String prefix,String suffix) 根据指定的分隔符,前缀,后缀创建StringJoiner对象

# 成员方法

方法名 说明
public StringJoiner add(String value) 将指定的字符串追加到当前字符串的末尾
public StringJoiner setEmptyValue(String emptyValue) 设置空值
public String toString() 将当前StringJoiner对象转换为字符串

注意

  • setEmptyValue设置确定此StringJoiner的字符串表示形式且尚未添加任何元素(即当它为空时)时要使用的字符序列。
  • 一旦调用了add方法,即使添加的元素对应于空字符串,StringJoiner也不再被认为是空的。
public class main {
    public void main(String[], args) {
        //字符串StringJoiner类相关

        //add方法 将指定的字符串添加到当前字符串的末尾
        StringJoiner str = new StringJoiner(",", "[", "]");
        str.add("Hello").add("World");
        System.out.println(str);//[Hello,World]

        //setEmptyValue方法 设置空值
        StringJoiner str1 = new StringJoiner("", "[", "]");
        str1.setEmptyValue("空值");
        System.out.println(str1);//空值


        //toString方法 将当前字符串对象转换为字符串
        StringJoiner str2 = new StringJoiner(",", "[", "]");
        str2.add("Hello").add("World");
        System.out.println(str2.toString());//[Hello,World]
    }
}

# 字符串原理

# 字符串存储内存原理

  • 直接复制会复用字符串常量池中的
  • new出来的不会复用,而是开辟一个新的空间

# ==号比较的到底是什么

  • 基本数据类型:比较的是值
  • 引用数据类型:比较的是地址值

# 字符串拼接底层原理

  • 在Jdk8之前,字符串直接用+拼接,底层是调用了StringBuilderappend方法
  • 每一个+都会创建一个新的StringBuilder对象,然后调用append方法,最后将结果转换为字符串 因此效率较低
  • 在Jdk8之后,会对字符串拼接进行预估,然后创建一个StringBuilder对象调用toString方法
  • 因此字符串拼接推荐直接使用StringBuilder类或StringJoiner

# 总结

  • 如果没有变量参与,都是字符串直接相加,编译之后就是拼接之后的结果,会复用串池中的字符串
  • 如果有变量参与,每一行拼接的代码,都会在内存中创建新的字符串,浪费内存

# StringBuilder提高效率原理图

  • 默认会创建一个长度为16的字节数组
  • 添加的内容长度小于16,则直接存储到数组中
  • 添加的内容长度大于16,则会扩容(原来的容量*2+2)
  • 如果扩容的容量还不够,
public class main {
    public void main(String[], args) {
        //无数据
        StringBuilder str = new StringBuilder();
        System.out.println(str.capacity());//16
        System.out.println(str.length());//0

        //添加abc
        str.append("abc");
        System.out.println(str.capacity());//16
        System.out.println(str.length());//3

        //扩容 16*2+2=34
        str.append("defghijklmnopqrstuvwsyz");
        System.out.println(str.capacity());//34
        System.out.println(str.length());//26

        //继续扩容 34*2+2=70
        str.append("1234567890");
        System.out.println(str.capacity());//70
        System.out.println(str.length());//36

        //扩容到一定程度则以字符串的实际长度为准
        str.append("90909090909090909645645645645645645645645645645645645645666666666666666666666");
        System.out.println(str.capacity());//113
        System.out.println(str.length());//113
    }
}
上次更新: 2/9/2025, 6:54:50 PM