1. StringBuilder 概述
1.1 什么是 StringBuilder
与 String
相似,StringBuilder
也是一个与字符串相关的类,Java 官方文档给 StringBuilder
的定义是:可变的字符序列。
1.2 为什么需要 StringBuilder
在 Java 字符串的学习中,我们知道了字符串具有不可变性,当频繁操作字符串时候,会在常量池中产生很多无用的数据(回忆图示)。
而 StringBuilder
与 String
不同,它具有可变性。相较 String
类不会产生大量无用数据,性能上会大大提高。
因此对于需要频繁操作字符串的场景,建议使用 Stringbuilder
类来代替 String
类。
2. StringBuffer 概述
2.1 定义
了解了 StringBuilder
类 ,StringBuffer
也是不得不提的一个类,Java 官方文档给出的定义是:线程安全的可变字符序列。
2.2 与前者的区别
StringBuffer
是 StringBuilder
的前身,在早期的 Java
版本中应用非常广泛,它是 StringBuilder
的线程安全版本(线程我们将在后面的小节中介绍),但实现线程安全的代价是执行效率的下降。
你可以对比 StringBuilder
和 StringBuffer
的接口文档,它们的接口基本上完全一致。为了提升我们代码的执行效率,在如今的实际开发中 StringBuffer
并不常用。因此本小节的重点在 StringBuilder
的学习。
3. StringBuilder 的常用方法
3.1 构造方法
StringBuilder
类提供了如下 4 个构造方法:
StringBuilder()
构造一个空字符串生成器,初始容量为 16 个字符;StringBuilder(int catpacity)
构造一个空字符串生成器,初始容量由参数capacity
指定;StringBuilder(CharSequence seq)
构造一个字符串生成器,该生成器包含与指定的CharSequence
相同的字符。;StringBuilder(String str)
构造初始化为指定字符串内容的字符串生成器。
其中第 4 个构造方法最为常用,我们可以使用 StringBuilder
这样初始化一个内容为 hello
的字符串:
- 1
3.2 成员方法
StringBuilder
类下面也提供了很多与 String
类相似的成员方法,以方便我们对字符串进行操作。下面我们将举例介绍一些常用的成员方法。
3.2.1 字符串连接
可以使用 StringBuilder
的 StringBuilder append(String str)
方法来实现字符串的连接操作。
我们知道,String
的连接操作是通过 +
操作符完成连接的:
- 1
- 2
- 3
如下是通过 StringBuilder
实现的字符串连接示例:
运行结果:
- 1
由于 append()
方法返回的是一个 StringBuilder
类型,我们可以实现链式调用。例如,上述连续两个 append()
方法的调用语句,可以简化为一行语句:
- 1
如果你使用 IDE
编写如上连接字符串的代码,可能会有下面这样的提示(IntelliJ idea 的代码截图):
提示内容说可以将 StringBuilder
类型可以替换为 String
类型,也就是说可以将上边地代码改为:
- 1
这样写并不会导致执行效率的下降,这是因为 Java 编译器在编译和运行期间会自动将字符串连接操作转换为 StringBuilder
操作或者数组复制,间接地优化了由于 String
的不可变性引发的性能问题。
值得注意的是,append()
的重载方法有很多,可以实现各种类型的连接操作。例如我们可以连接 char
类型以及 float
类型,实例如下:
运行结果:
- 1
上面代码里连续的两个 append()
方法分别调用的是重载方法 StringBuilder append(char c)
和 StringBuilder append(float f)
。
3.2.2 获取容量
可以使用 int capacity()
方法来获取当前容量,容量指定是可以存储的字符数(包含已写入字符),超过此数将进行自动分配。注意,容量与长度(length)不同,长度指的是已经写入字符的长度。
例如,构造方法 StringBuilder()
构造一个空字符串生成器,初始容量为 16 个字符。我们可以获取并打印它的容量,实例如下:
运行结果:
- 1
- 2
3.2.3 字符串替换
可以使用 StringBuilder replace(int start, int end, String str)
方法,来用指定字符串替换从索引位置 start
开始到 end
索引位置结束(不包含 end
)的子串。实例如下:
运行结果:
- 1
也可使用 StringBuilder delete(int start, int end)
方法,先来删除索引位置 start
开始到 end
索引位置(不包含 end
)的子串,再使用 StringBuilder insert(int offset, String str)
方法,将字符串插入到序列的 offset
索引位置。同样可以实现字符串的替换,例如:
- 1
- 2
- 3
3.2.4 字符串截取
可以使用 StringBuilder substring(int start)
方法来进行字符串截取,例如,我们想截取字符串的后三个字符,实例如下:
运行结果:
- 1
如果我们想截取示例中的” 欢迎 “二字,可以使用重载方法 StringBuilder substring(int start, int end)
进行截取:
- 1
3.2.5 字符串反转
可以使用 StringBuildr reverse()
方法,对字符串进行反转操作,例如:
运行结果:
- 1
4. 小结
本小节我们介绍了 Java 的 StringBuilder
类,它具有可变性,对于频繁操作字符串的场景,使用它来代替 String
类可以提高程序的执行效率;也知道了 StringBuffer
是 StringBuilder
的线程安全版本,官方更推荐使用 StringBuilder
;最后我们介绍了 StringBuilder
的常用构造方法和成员方法,如果你想了解更多关于 StringBuilder
的接口,可以翻阅官方文档进行学习。