三者区别
String 不可变字符串,另外两个是可变的。
StringBuffer 可变字符串,是线程安全的内部用的synchronized 做的线程安全。
StringBuilder 可变字符串,非线程安全。
从类关系图看
![df4e351ad9396c26e36f7f57403b877e.png](https://i-blog.csdnimg.cn/blog_migrate/046ef3c3753c5b715fc489f26ae53e63.jpeg)
String类图
![c478ae73168321a96855698f892df4dd.png](https://i-blog.csdnimg.cn/blog_migrate/e43f926d088c1a57b7f8f15a870994ce.jpeg)
StringBuffer类图
![24c1da5afe15a8402f769f2ebc91a418.png](https://i-blog.csdnimg.cn/blog_migrate/0c98d4d8ac28b6bae934edfb7067b753.jpeg)
StringBuilder类图
CharSequence
![acdec72c987f03a5a8fa312269ead8f9.png](https://i-blog.csdnimg.cn/blog_migrate/3ceed7808d45859e719957cf9135b03e.jpeg)
CharSequence中的方法
可以看到String、StringBuffer与StringBuilder都实现了CharSequence接口。
CharSequence是一个接口,表示char值的一个可读序列。此接口对许多不同种类的char序列提供统一的自读访问。此接口不修改该equals和hashCode方法的常规协定,因此,通常未定义比较实现CharSequence 的两个对象的结果。
CharSequence与String都能用于定义字符串,但CharSequence的值是可读可写序列,而String的值是只读序列。
对于一个抽象类或者是接口类,不能使用new来进行赋值,但是可以通过以下的方式来进行实例的创建:CharSequence cs = "pine";
Appendable
![4507c7ec69d05683269adf32b3f1a6a9.png](https://i-blog.csdnimg.cn/blog_migrate/34e2d33bbb9cacf4737f62b1f3f42791.jpeg)
Appendable接口中的方法
明显能够看到主要是用于定义拼接方法的接口类。
下面看一个append实现方法。
@Overridepublic AbstractStringBuilder append(CharSequence s, int start, int end) { if (s == null) s = "null"; if ((start < 0) || (start > end) || (end > s.length())) throw new IndexOutOfBoundsException( "start " + start + ", end " + end + ", s.length() " + s.length()); int len = end - start; ensureCapacityInternal(count + len); for (int i = start, j = count; i < end; i++, j++) value[j] = s.charAt(i); count += len; return this;}
从方法中不难看出为啥我们拼接为NULL的对象是为啥拼接的字符串是“null”了。
另外Formatter相关的类也会实现Appendable接口。