Java中常用来处理字符串的类有三个: String, StringBuffer和StringBuilder.

区别

三者都继承自CharSequence接口, 首先说明三者间主要区别

  • String字符串常量
  • StringBuffer字符串变量(线程安全)
  • StringBuilder字符串变量(线程不安全)

String

在Java中String对象是不可变的. 每次改变String类型的时候都会生成一个新的String对象, 然后将指针指向新的String对象.

如下代码中, str最终的值"ab"并非str所引用对象的内容发生了变化, 而是str在执行的过程中重新引用了另外一个String对象"ab". 并且String的+操作, 会转化成StringBuilder的append()方法来实现.

String str = "a";
str += "b";

特别的, 如果代码如下这样直接拼接字符串的话, 在编译过程中JVM会直接优化成把str的引用指向"ab".

String str = "a" + "b";

StringBuilder和StringBuffer

StringBuffer和StringBuilder都可变, 区别在于StringBuilder是线程不安全的, 而StringBuffer的API前多了一个synchronized关键字, 所以StringBuffer是线程安全的. 所谓的线程安全就是在多线程中多个线程同时操作一个对象不会出现问题. 然而真实的应用场景中, 还真没怎么见过有多个线程轮流操作一个字符串的情况.

实际上StringBuilder是在JDK 1.5中才加上的, 之前只有StringBuffer, 写过几年C#的我很是怀疑StringBuilder的这个命名是从C#借鉴来的. 至于为什么先有一个线程安全的StringBuffer后来再有一个线程不安全的StringBuilder, 而且从两者的命名来看你压根区分不出哪个是线程安全的, 个人感觉这应该是一个设计失误吧...

StringBuffer和StringBuilder都继承自AbstractStringBuilder, 而AbstractStringBuilder里有个expandCapacity方法用来扩容, 这就导致了StringBuffer和StringBuilder中另外一个重要的问题, 就是初始化时的容量问题.

StringBuilder扩容的问题

在StringBuilder中有一个char[], 初始的容量是16. 那么问题来了, 如果要append的长度超过了16, 会发生什么?

答案是会调用expandCapacity, 成倍扩容! 所以在高性能场景下StringBuilder的初始长度很重要很重要.

void expandCapacity(int minimumCapacity) {
int newCapacity = value.length * 2 + 2;
if (newCapacity - minimumCapacity < 0)
newCapacity = minimumCapacity;
if (newCapacity < 0) {
if (minimumCapacity < 0) // overflow
throw new OutOfMemoryError();
newCapacity = Integer.MAX_VALUE;
}
value = Arrays.copyOf(value, newCapacity);
}

初始长度太小扩容时会带来时间消耗, 初始长度太大又会带来空间消耗. 可以参考这里的用法来复用StringBuilder.

Java中String, StringBuilder和StringBuffer的更多相关文章

  1. JAVA 中的 StringBuilder 和 StringBuffer 适用的场景是什么?

    JAVA 中的 StringBuilder 和 StringBuffer 适用的场景是什么? 最简单的回答是,stringbuffer 基本没有适用场景,你应该在所有的情况下选择使用 stringbu ...

  2. java中String StringBuilder StringBuffer比较和效率(性能)测试

    string stringbuilder stringbuffer三者的区别 从JDK源码看,String.StringBuilder.StringBuffer都是存放在char[] 数组字符串. 简 ...

  3. Java中测试StringBuilder、StringBuffer、String在字符串拼接上的性能

    应一个大量字符串拼接的任务 测试一下StringBuilder.StringBuffer.String在操作字符串拼接时候的性能 性能上理论是StringBuilder  >  StringBu ...

  4. java中string stringbuilder stringbuffer 的区别

    1. String 类 String的值是不可变的,这就导致每次对String的操作都会生成新的String对象,不仅效率低下,而且大量浪费有限的内存空间. String a = "a&qu ...

  5. Java中的StringBuilder和StringBuffer适用场景

    我不知道为什么这个这么老的问题会出现在我的时间线上,看了一下回答,大多是2012,2013年的回答,照说那个年代,有些历史故事还很新鲜,却不知道为什么没有一个答案说到点子上. stringbuffer ...

  6. java中String、StringBuffer、StringBuilder的区别

    java中String.StringBuffer.StringBuilder是编程中经常使用的字符串类,他们之间的区别也是经常在面试中会问到的问题.现在总结一下,看看他们的不同与相同. 1.可变与不可 ...

  7. 探秘Java中String、StringBuilder以及StringBuffer

    探秘Java中String.StringBuilder以及StringBuffer 相信String这个类是Java中使用得最频繁的类之一,并且又是各大公司面试喜欢问 到的地方,今天就来和大家一起学习 ...

  8. java中String类、StringBuilder类和StringBuffer类详解

    本位转载自http://www.cnblogs.com/dolphin0520/p/3778589.html  版权声明如下: 作者:海子 出处:http://www.cnblogs.com/dolp ...

  9. Java中string拼接,StringBuilder,StringBuffer和+

    Java中string拼接,StringBuilder,StringBuffer和+,到底哪个更合适? StringBuilder线程不安全,效率较线程安全的StringBuffer高.jdk1.5之 ...

随机推荐

  1. Burp Post、Get数据包转为上传multipart/form-data格式数据包

    方法一: 新建一个网页进行上传,代码代码如下: <html> <head></head> <body> <form method="po ...

  2. [XPath] XPath 与 lxml (一)XPath 术语

    前言 这是一篇主要介绍 XPath 的文章,由于 JQuery 已经不支持 XPath,所以本文主要通过 Python 的 lxml.etree 来介绍 XPath. 什么是 XPath ? XPat ...

  3. iOS添加自定义字体

    字体有相应的字体文件,一般是以ttf或者otf为后缀,我们可以去一些第三方网站去下载(也有人专门做了字体出售),Google Fonts是个比较好的网站,可以去找找看.我们就用Open Sans这个字 ...

  4. 转:git windows中文目录乱码问题解决

    Git的Windows版本Msysgit对中文的支持不够好 当使用时,会出现以下三种情况的中文乱码: 1.ls不能显示中文目录 解决办法:在git/git-completion.bash中增加一行:  ...

  5. thinkphp3.2 实现二级导航和高亮显示

    一.控制器代码如下: public function index(){ //高亮显示 $action = CONTROLLER_NAME."/".ACTION_NAME; $thi ...

  6. 【技术分享会】 @第七期 android开发基础

    前言 Android是一种基于Linux的自由及开放源代码的操作系统,主要使用于移动设备,如智能手机和平板电脑,由Google公司和开放手机联盟领导及开发. Android 软件系列包括操作系统.中间 ...

  7. Find–atime –ctime –mtime的用法与区别总结

    转自 周五有同事问起find命令中-mtime n.-mtime –n以及-mtime +n的用法区别,当时虽然记得这里n是n个24个小时的意思,也是对所有这几个属性详细的用法却一知半解,索性周末仔细 ...

  8. Post Office Protocol --- pop协议

    https://en.wikipedia.org/wiki/Simple_Mail_Transfer_Protocol

  9. git查看指令

    打开git bash 1,查看自己之前是否生成过ssh密钥 $ ls .ssh 如果存在这个id_rsa.pub这个文件的话表示已经生成了 2,查看用户名和邮箱 $ git config --glob ...

  10. Linux下socket最大连接数 ulimit -n 最大值修改

    请求多的Linux服务器,如不改最大打开文件数的话,那是一个悲剧~可以用命令 ulimit -n 看看当前最大可打开文件数 默认是1024如果加大呢?临时方法是ulimit -n 8192 这个方法是 ...