|
5 | 5 |
|
6 | 6 | **可变性**
|
7 | 7 |
|
8 |
| -String类中使用字符数组:`private final char value[]`保存字符串,所以String对象是不可变的。StringBuilder与StringBuffer都继承自AbstractStringBuilder类,在AbstractStringBuilder中也是使用字符数组保存字符串,char[]value,这两种对象都是可变的。 |
9 |
| - |
| 8 | + |
| 9 | +简单的来说:String 类中使用 final 关键字字符数组保存字符串,`private final char value[]`,所以 String 对象是不可变的。而StringBuilder 与 StringBuffer 都继承自 AbstractStringBuilder 类,在 AbstractStringBuilder 中也是使用字符数组保存字符串`char[]value` 但是没有用 final 关键字修饰,所以这两种对象都是可变的。 |
| 10 | + |
| 11 | +StringBuilder 与 StringBuffer 的构造方法都是调用父类构造方法也就是 AbstractStringBuilder 实现的,大家可以自行查阅源码。 |
| 12 | + |
| 13 | +AbstractStringBuilder.java |
| 14 | + |
| 15 | +```java |
| 16 | +abstractclassAbstractStringBuilderimplementsAppendable,CharSequence { |
| 17 | +char[] value; |
| 18 | +int count; |
| 19 | +AbstractStringBuilder() { |
| 20 | + } |
| 21 | +AbstractStringBuilder(intcapacity) { |
| 22 | + value=newchar[capacity]; |
| 23 | + } |
| 24 | +``` |
| 25 | + |
10 | 26 |
|
11 | 27 | **线程安全性**
|
12 | 28 |
|
13 |
| -String中的对象是不可变的,也就可以理解为常量,线程安全。AbstractStringBuilder是StringBuilder与StringBuffer的公共父类,定义了一些字符串的基本操作,如expandCapacity、append、insert、indexOf等公共方法。StringBuffer对方法加了同步锁或者对调用的方法加了同步锁,所以是线程安全的。StringBuilder并没有对方法进行加同步锁,所以是非线程安全的。 |
| 29 | +String 中的对象是不可变的,也就可以理解为常量,线程安全。AbstractStringBuilder 是StringBuilder 与StringBuffer 的公共父类,定义了一些字符串的基本操作,如 expandCapacity、append、insert、indexOf 等公共方法。StringBuffer 对方法加了同步锁或者对调用的方法加了同步锁,所以是线程安全的。StringBuilder 并没有对方法进行加同步锁,所以是非线程安全的。 |
14 | 30 |
|
15 | 31 |
|
16 | 32 | **性能**
|
17 | 33 |
|
18 |
| -每次对String类型进行改变的时候,都会生成一个新的String对象,然后将指针指向新的String对象。StringBuffer每次都会对StringBuffer对象本身进行操作,而不是生成新的对象并改变对象引用。相同情况下使用StirngBuilder 相比使用StringBuffer 仅能获得10%~15% 左右的性能提升,但却要冒多线程不安全的风险。 |
| 34 | +每次对String类型进行改变的时候,都会生成一个新的String 对象,然后将指针指向新的String对象。StringBuffer 每次都会对StringBuffer 对象本身进行操作,而不是生成新的对象并改变对象引用。相同情况下使用StirngBuilder 相比使用StringBuffer 仅能获得10%~15% 左右的性能提升,但却要冒多线程不安全的风险。 |
19 | 35 |
|
20 | 36 | **对于三者使用的总结:**
|
21 |
| - |
22 |
| -- 如果要操作少量的数据用 = String |
23 |
| -- 单线程操作字符串缓冲区 下操作大量数据 = StringBuilder |
24 |
| -- 多线程操作字符串缓冲区 下操作大量数据 = StringBuffer |
| 37 | +1. 操作少量的数据=String |
| 38 | +2. 单线程操作字符串缓冲区下操作大量数据=StringBuilder |
| 39 | +3. 多线程操作字符串缓冲区下操作大量数据=StringBuffer |
25 | 40 |
|
26 | 41 | ####String为什么是不可变的吗?
|
27 | 42 | 简单来说就是String类利用了final修饰的char类型数组存储字符,源码如下图所以:
|
|