谈一谈String、StringBuffer和StringBuilder的区别

来源:互联网 发布:58同城网络兼职 编辑:程序博客网 时间:2024/05/16 16:05
 在我们编写代码的过程中经常会使用到String字符串,但是在有些特定的情况下我们的String就难以胜任了,因此我们这个时候就会去选择StringBuffer和StringBuilder,那么,我们到底应该如何在不同的情况下正确的选择使用呢?
   首先,我们来分析一下它们区别:
一:是否是可变的

1.String字符串是我们最早接触,也是使用最广的,但是对它是否可变这一点大家的概念可能有点模糊。其实,我们的String是不可变的,我们视它默认被final(常量,不可变的量)所修饰,因此,我们的String是不可变的。

  可能有人会说String怎么是不可变的呢?想要使String变动很简单啊。

 public static voidmain(String[] args) {                                  String str = "abc"+"sda"+"sda";                                  String str2 = "lkj";                                  String str3 = "mnb";                                  str = str2+str3;                 }

上面的这两种方法的确可以对我们的String进行添加,第一种直接在后面使用“+”号连接,第二种则是创建新的变量然后将他们用“+”连接。不可否认,这样的确是可以变化String当中的值,但是这样的做法是有局限性的:
  (1).不能随时变化(一个项目中代码不可能只有几行,那么如果在编写的过程中突然想起前面有一个String变量需要对它进行频繁的修改呢?显然我们的String就做不到)。
  (2).第二种方法创建新的变量然后将他们用“+”连接,这样的做法是极其消耗内存的,因为每次创建都等于是new了一个新对象开辟了一个新的存储空间,虽然说JAVA有垃圾回收机制,但如果你要添加修改上万次呢?这样造成的压力是巨大的,一个好的程序是不允许这样多余的性能消耗的。
  (3).这两种方法只能是对String进行添加,并且只能在末尾进行添加。
  由此可见我们的String是不可变的。

  2.StringBuilder与StringBuffer类是可变的
Stringbuffer

public final class StringBuffer       extends AbstractStringBuilder       implements java.io.Serializable, CharSequence

StringBuilder

public final class StringBuilder       extends AbstractStringBuilder       implements java.io.Serializable, CharSequence

从上面红色字体可以发现,我们的StringBuilder与StringBuffer都是继承了AbstractStringBuilder,它们都可以通过例如:append和insert的方法添加字符。其中append 方法始终将这些字符添加到缓冲区的末端,方法则在指定的下标点添加字符(在中间任何位置添加字符).
append()和insert()方法的使用:

public class StringTest {       public static void main(String[] args) {           StringBuffer Sb = new StringBuffer("abc");           Sb.append("fde");           Sb.insert(1,"y");           System.out.println(Sb);       }   }

所以这里我们可以得出结论,String是不可变的,StringBuilder与StringBuffer类是可变的。

二:线程是否安全:

  1.String中的对象是不可变的,我们视它为被final所修饰的量,作为不可变的量,线程显然也是安全的。

  2.StringBuffer类在JAVA开发的源码中对方法和调用方法加了同步锁,因此线程也是安全的

        public synchronized int length() {            return count;            }        public synchronized int capacity() {           return value.length;           }        public synchronized void ensureCapacity(int minimumCapacity) {          if (minimumCapacity > value.length) {            expandCapacity(minimumCapacity);           }        }    /**     * @since      1.5     */         public synchronized void trimToSize() {           super.trimToSize();         }
上面是JAVA开发源码(由于太多就不全部截图了),大家可以看到,在我们Stringbuffer的方法定义的时候都被加上了同步(synchronized),这样使我们Stringbuffer的线程变得安全,可以有效的应对高并发的情况发生。

  3.Stringbuilder类并没有像Stringbuffer一样添加的同步锁,所以我们StringBuilder线程是不安全的。

  所以这里我们可以得出,String和Stringbuffer是线程安全的,但是Stringbuilder是线程不安全的。

  现在我们已经知道了它们的区别于特点,那么我们应该在不同的情况下怎样正确的选择使用呢?
1.在操作少量数据的时候使用String ;单线程操作大量数据使用StringBuilder ;多线程操作大量数据考虑线程安全的时候使用StringBuffer。

2.不要使用String类的"+"来进行频繁的拼接,因为那样会造成极大的资源浪费,应该使用StringBuffer或StringBuilder类,这在Java的优化上是一条比较重要的原则。

上面就是小猪的一些个人总结与见解,希望能给大家带来帮助,如果有错误的地方希望大家及时指正我也会积极修改,如果有疑问的朋友或者希望共同学习进步的朋友可以添加扣群:378303386 在这里有着一群和你一样求知的小伙伴们等待着共同讨论进步。也可以添加我扣:2714491282


原创粉丝点击