java源码解读之String,StringBuilder,StringBuffer

由于最近正好毕业了,正在找工作~~~参加了几场面试,发现好多公司都会问String,StringBuilder,StringBuffer三者之间的区别~~说实话,以前没了解过,所以不知道,其实网上很多都有相关的介绍,但是不理解为什么!所以今天就打算从源代码看看三者之间的区别~~~

首先看一下String的源码:

我们可以看出,String是一个final类型的一个类,不可以被继承。同时,String底层由char数组实现的~~~

我们先来看一下这个代码

String s1 =new String("abc")

以上会产生几个对象呢?

这是面试中经常出现的一个问题~~~

答案是:两个

为什么呢?我们来看一下源码:

 public String(String original) {        this.value = original.value;        this.hash = original.hash;    }

我们可以看你出来,String s1=new String("abc");其实就是将“abc”产生一个对象,并且把该对乡复制给s1对象~~~

这就是产生两个对象的原因!!!

同时呢,String产生之后的长度是不可改变的~~~那就有同学问了,s1+=s2是怎么回事?

其实,那是s1+s2产生一个新的String对象s1,原来的s1对象已经被废弃掉了~~~~

其实,这样效率非常的低的~~

而且在多线程的环境下是非同步的,也就是不安全的~~

这就是好多都推荐用StringBuffer或者StringBuilder的原因了~~~

我们看一下StringBuffer的源码:

StringBuffer继承于absractStringBuilder

创建方式有四种,其 中StringBuffer sb=new StringBuffer("qqqqq")的创建方式,是将String的长度+16产生一个新的StringBuffer对象,然后在调用apppend()方法将“qqqq”追加到StringBuffer对象中,那我们看一下append()的源码:

 public synchronized StringBuffer append(String str) {        super.append(str);        return this;    }
  public AbstractStringBuilder append(String str) {        if (str == null) str = "null";        int len = str.length();        ensureCapacityInternal(count + len);        str.getChars(0, len, value, count);        count += len;        return this;    }

private void ensureCapacityInternal(int minimumCapacity) {        // overflow-conscious code        if (minimumCapacity - value.length > 0)            expandCapacity(minimumCapacity);    }
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);    }

append()方法内部直接就是调用父类的absractStringBuilder中的append(),在父类的append()中,首先判断追加后数组的长度是否超出现有长度,超出的话,就将

现有的数组产度扩充为:现有长度*2+2 ,然后在将内容复制到新数组中!!

可见,StringBuffer对象是可变的,长度可变不唯一,递增规则就是:现有长度*2+2

这样的话,效率上事要比String要高很多的~~~~

同时,StringBuffer的所用方法都是由synchronized关键字修饰,是线程安全的。

我们接下来看一下StringBuilder的源码:

是不是很熟悉阿?对!StringBuilder和StringBuffer在实现上基本一致,唯一一点区别就是StringBuilder是线程不安全的!!

这就是为什么两者的效率为什么基本一样的原因~~~~

OK,这样想必大家就对三者之间的关系有所理解了把~~~

去看日出,去散步,去欣赏大自然,

java源码解读之String,StringBuilder,StringBuffer

相关文章:

你感兴趣的文章:

标签云: