String类
String是Java开发中非常高频使用的一个类
重要
它有两个子类,StringBuffer 和 StringBuilder 在项目中也会被高频使用
classDiagram
    class String {
        -final char[] value
        +length() int
        +charAt(int) char
        +substring(int) String
        +equals(Object) boolean
    }
    class StringBuilder {
        +append(String) StringBuilder
        +toString() String
    }
    class StringBuffer {
        +append(String) StringBuffer
        +toString() String
    }
    String <.. StringBuilder
    String <.. StringBuffer
对比
| 特点 | String | StringBuilder | StringBuffer | 
|---|---|---|---|
| 可变性 | 不可变 | 可变 | 可变 | 
| 线程安全 | 是 | 否 | 是 | 
| 性能 | 较差 | 最好 | 较好 | 
| 适用场景 | 少量字符串操作 | 单线程大量字符串操作 | 多线程大量字符串操作 | 
| 内存使用 | 每次修改都创建新对象 | 动态扩容,内存效率高 | 动态扩容,内存效率高 | 
| 同步机制 | 不需要 | 不需要 | 需要 | 
| 初始容量 | 无 | 16 | 16 | 
| 扩容策略 | 不适用 | 2倍+2 | 2倍+2 | 
示例代码
public class StringDemo {
    public static void main(String[] args) {
        // 字符串创建
        String s1 = "hello"; // 字符串常量池
        String s2 = new String("hello"); // 堆中新对象
        String s3 = "hello";
        // == 和 equals比较
        System.out.println("s1 == s2: " + (s1 == s2)); // false
        System.out.println("s1 == s3: " + (s1 == s3)); // true
        System.out.println("s1 equals s2: " + s1.equals(s2)); // true
        // 常用方法
        System.out.println("长度: " + s1.length());
        System.out.println("拼接: " + s1.concat(" world"));
        System.out.println("子串: " + "hello".substring(1, 3)); // el
        System.out.println("替换: " + "hello".replace('l', 'L')); // heLLo
        System.out.println("分割: " + Arrays.toString("a,b,c".split(",")));
        // 字符串拼接性能
        long start = System.currentTimeMillis();
        String result = "";
        for(int i = 0; i < 10000; i++) {
            result += i; // 性能差,每次创建新对象
        }
        long end = System.currentTimeMillis();
        System.out.println("普通拼接耗时: " + (end - start) + "ms");
        // 使用StringBuilder优化
        start = System.currentTimeMillis();
        StringBuilder sb = new StringBuilder();
        for(int i = 0; i < 10000; i++) {
            sb.append(i);
        }
        end = System.currentTimeMillis();
        System.out.println("StringBuilder耗时: " + (end - start) + "ms");
        // 其他常用方法
        System.out.println("是否包含: " + "hello".contains("ell")); // true
        System.out.println("去除空格: " + " hello ".trim()); // hello
        System.out.println("格式化: " + String.format("姓名:%s, 年龄:%d", "张三", 25));
    }
}
public class StringBufferDemo {
    public static void main(String[] args) {
        // 创建StringBuffer对象
        StringBuffer sb = new StringBuffer();
        // 追加字符串
        sb.append("Hello");
        sb.append(" ");
        sb.append("World");
        System.out.println("追加后: " + sb.toString());
        // 插入字符串
        sb.insert(5, " Java");
        System.out.println("插入后: " + sb.toString());
        // 删除字符串
        sb.delete(5, 10);
        System.out.println("删除后: " + sb.toString());
        // 替换字符串
        sb.replace(0, 5, "Hi");
        System.out.println("替换后: " + sb.toString());
        // 反转字符串
        sb.reverse();
        System.out.println("反转后: " + sb.toString());
        // 设置长度
        sb.setLength(5);
        System.out.println("设置长度后: " + sb.toString());
        // 获取容量
        System.out.println("当前容量: " + sb.capacity());
        // 确保容量
        sb.ensureCapacity(50);
        System.out.println("确保容量后: " + sb.capacity());
    }
}
public class StringBuilderDemo {
    public static void main(String[] args) {
        // 创建StringBuilder对象
        StringBuilder sb = new StringBuilder();
        // 追加字符串
        sb.append("Hello");
        sb.append(" ");
        sb.append("World");
        System.out.println("追加后: " + sb.toString());
        // 插入字符串
        sb.insert(5, " Java");
        System.out.println("插入后: " + sb.toString());
        // 删除字符串
        sb.delete(5, 10);
        System.out.println("删除后: " + sb.toString());
        // 替换字符串
        sb.replace(0, 5, "Hi");
        System.out.println("替换后: " + sb.toString());
        // 反转字符串
        sb.reverse();
        System.out.println("反转后: " + sb.toString());
        // 设置长度
        sb.setLength(5);
        System.out.println("设置长度后: " + sb.toString());
        // 获取容量
        System.out.println("当前容量: " + sb.capacity());
        // 确保容量
        sb.ensureCapacity(50);
        System.out.println("确保容量后: " + sb.capacity());
        // 链式调用
        StringBuilder chain = new StringBuilder()
            .append("Hello")
            .append(" ")
            .append("World")
            .insert(5, " Java")
            .delete(5, 10)
            .replace(0, 5, "Hi");
        System.out.println("链式调用结果: " + chain.toString());
    }
}
使用场景
String使用场景
- 
字符串常量定义
String name = "张三"; String path = "/api/v1/users"; - 
字符串比较和查找
if (userName.equals("admin")) { // 处理管理员逻辑 } - 
字符串分割和截取
String[] parts = "a,b,c".split(","); String sub = "hello".substring(0, 2); - 
字符串格式化
String message = String.format("用户%s的年龄是%d", name, age); 
StringBuilder使用场景
- 
大量字符串拼接
StringBuilder sql = new StringBuilder(); sql.append("SELECT * FROM users WHERE 1=1"); if (name != null) { sql.append(" AND name = '").append(name).append("'"); } - 
动态构建HTML/XML
StringBuilder html = new StringBuilder(); html.append("<div>") .append("<h1>").append(title).append("</h1>") .append("<p>").append(content).append("</p>") .append("</div>"); - 
日志信息构建
StringBuilder log = new StringBuilder(); log.append("用户登录失败:") .append("用户名=").append(username) .append(", IP=").append(ip) .append(", 时间=").append(new Date()); 
StringBuffer使用场景
- 
多线程环境下的字符串操作
public class LogBuffer { private StringBuffer buffer = new StringBuffer(); public synchronized void appendLog(String message) { buffer.append(new Date()).append(": ").append(message).append("\n"); } } - 
线程安全的字符串构建器
public class ThreadSafeBuilder { private StringBuffer buffer = new StringBuffer(); public void buildMessage(String part) { buffer.append(part); } public String getResult() { return buffer.toString(); } } - 
并发环境下的日志记录
public class ConcurrentLogger { private StringBuffer logBuffer = new StringBuffer(); public void log(String message) { synchronized(logBuffer) { logBuffer.append(Thread.currentThread().getName()) .append(": ") .append(message) .append("\n"); } } } 
选择建议
- 如果字符串内容固定,使用String
 - 如果单线程下需要频繁修改字符串,使用StringBuilder
 - 如果多线程下需要频繁修改字符串,使用StringBuffer
 - 如果字符串操作次数较少,直接使用String即可
 - 如果字符串操作次数较多,优先考虑StringBuilder(单线程)或StringBuffer(多线程)