字符串在开发中经常使用到, 但是 Java 中提供三种字符串操作的类, String,StringBuffer 以及 StringBuilder, 那么它们有什么区别以及怎么使用呢?
从概念上讲, Java 字符串就是 Unicode 字符序列, 例如, 串 "Java\u2122" 由 5 个 Unicode 字符 J,a,v,a 和 TM .Java 没有内置的字符串类型, 而是在标准 Java 类库中提供了一个预定义类, 很自然的叫做 String. 每个双引号 "" 括起来的字符串都是 String 类的一个实例:
- String e = ""; //an empty string
- String greeting = "Hello";
那么这三者的区别是什么?
1, 可变性
查看源码简单来说, String 类中使用 final 关键字修饰的字符数组保存字符串, 所以 String 对象是不可变的:
String.java
- public final class String implements java.io.Serializable, Comparable<String>, CharSequence {
- private final char value[];
- private int hash;
- ...
- }
而 StringBuilder 和 StringBuffer 都继承自 AbstractStringBuilder, 在 AbstractStringBuilder 类中也是使用字符数组来保存字符串的, 但是没有用 final 关键字修饰:
AbstractStringBuilder.java
- abstract class AbstractStringBuilder implements Appendable, CharSequence {
- char[] value;
- int count;
- AbstractStringBuilder(){
- }
- AbstractStringBuilder(int capacity){
- valeu = new char[capacity];
- }
- ...
- }
StringBuilder.java
- public final class StringBuilder extends AbstractStringBuilder implements java.io.Serializable, CharSequence{
- public StringBuilder() {
- super(16);
- }
- ...
- }
StringBuffer.java
- public final class StringBuffer extends AbstractStringBuilder implements java.io.Serializable, CharSequence{
- private transient char[] toStringCache;
- public StringBuffer() {
- super(16);
- }
- ...
- }
从而也可以看出三个类也是用 final 修饰的, 所以是不可继承的.
2, 线程安全性
String 中的对象是不可变的, 也可以理解为常量, 线程安全. AbstractStringBuilder 是 StringBuilder 和 StringBuffer 的父类, 定义了一些字符串的基本操作, 如 expandCapacity,append,insert,indexOf 等公共方法. StringBuffer 对方法加了同步锁或者对调用的方法加了同步锁, 所以是线程安全的. 而 StringBuilder 并没有对方法加同步锁, 所以是线程不安全的.
3, 性能
每次对 String 进行改变的时候, 都会生成一个新的 String 对象, 然后将引用指向新的 String 对象. StringBuffer 和 StringBuilder 每次都是对对象本身进行操作, 而不生成新的对象也不改变引用的指向. 相同情况下使用 StringBuilder 相比使用 StringBuffer 仅能获得 10%-15% 左右的性能提升, 却要冒线程不安全的风险.
4, 使用建议
操作少量数据 String
单线程, 字符串缓冲区下操作大量数据 StringBuilder
多线程, 字符串缓冲区下操作大量数据 StringBuffer
5, 常用 API
- java.lang.String
- // 返回给定位置的代码单元.
- char charAt(int index)
- // 按照字典顺序, 如果字符串位于 other 之前, 返回一个负数; 如果字符串在 other 之后, 返回一个正数; 如果两个字符串相等, 返回 0.
- int compareTo(String other)
- // 用数组中 offset 开始的 count 个码点构成一个字符串
- new String(int[] codePoints, int offset, int count)
- // 如果字符串与 other 相等, 返回 true, 反之返回 false
- boolean equals(Object other)
- // 如果字符串与 other 相等 (忽略大小写), 返回 true, 反之返回 false
- boolean equalsIgnoreCase(String other)
- // 如果字符串以 prefix 开头, 返回 true
- boolean startsWith(String prefix)
- // 如果字符串以 suffix 结尾, 返回 true
- boolean endsWith(String suffix)
- // 返回字符串 str 或代码点 cp 匹配的第一个子串开始的位置. 这个位置从索引 0 或者 fromIndex 开始计算.
- // 如果在原始串中不存在 str, 返回 - 1
- int indexOf(String str)
- int indexOf(String str, int fromIndex)
- int indexOf(int cp)
- int indexOf(int cp, int fromIndex)
- // 返回字符串 str 或代码点 cp 匹配的最后一个子串开始的位置. 这个位置从原始串结尾端或 fromIndex 开始计算
- int lastIndexOf(String str)
- int lastIndexOf(String str, int fromIndex)
- int lastIndexOf(int cp)
- int lastIndexOf(int cp, int fromIndex)
- // 返回字符串的长度
- int length()
- // 返回一个新字符串. 这个字符串用 newString 代替原始字符串中所有 oldString.
- // 可以用 String 或 StringBuffer 或 StringBuilder 对象作为 CharSequence 参数.
- String replace(CharSequence oldString, CharSequence newString)
- // 返回一个新字符串. 这个字符串包含原始字符串中从 beginIndex 到串尾的所有代码单元
- String substring(int beginIndex)
- // 返回一个新字符串. 这个字符串包含原始字符串中从 beginIndex 到 endindex-1 的所有代码单元
- String substring(int beginIndex, int endIndex)
- // 返回一个新字符串. 这个字符串将原始字符串中的大写改为小写
- String toLowerCase()
- // 返回一个新字符串. 这个字符串将原始字符串中的小写改为大写
- String toUpperCase()
- // 返回一个新字符串. 这个字符串将删除原始字符串头部和尾部的空格
- String trim()
- // 返回一个新字符串. 用给定的定界符连接所有元素
- String join(CharSequence delimiter, CharSequence... elements)
- java.lang.StringBulider
- // 构造一个空字符串构建器
- StringBuilder()
- // 返回构建器或缓冲器中的代码单元数量
- int length()
- // 追加一个字符串并返回 this
- StringBuilder append(char c)
- // 将第 i 个代码单元设置为 c
- void setCharAt(int i, chanr c)
- // 在 offset 位置插入一个字符串并返回 this
- StringBuilder insert(int offset, String str)
- // 删除偏移量从 startIndex 到 endIndex-1 的代码单元并返回 this
- StringBuilder delete(int startIdnex, int endIndex)
- // 返回一个与构建器或缓冲器内容相同的字符串
- String toString()
- java.lang.StringBuffer
与 StringBuilder 基本相同
来源: http://www.bubuko.com/infodetail-3037883.html