StringBuffer(String str)和StringBuffer(CharSequence chars)的区别

4

1.我对这两个东西感到困惑,它们是否有不同的功能?如果是这样,那么它们有什么区别呢?

StringBuffer(CharSequence chars) 

并且。
StringBuffer(String str)

2. 字符串和CharSequence之间的基本区别是什么(特别是功能)?


很好的发现,我以为所有这样的东西都被移除了——String被替换成了CharSequences... - Betlista
http://grepcode.com/file/repository.grepcode.com/java/root/jdk/openjdk/6-b14/java/lang/StringBuffer.java#StringBuffer.%3Cinit%3E%28java.lang.String%29 - Maksym
@Maksym:它没有解释为什么有这个多余的构造函数,那个带有“String”的构造函数不需要存在... - Betlista
“那个带有String的不需要在这里。”为什么? - Maksym
1
@Avin 很好的问题。表明您正确理解了多态性和接口。 - Basil Bourque
@Maksym:因为String实现了CharSequence,所以它与第一个构造函数匹配...而且两者的实现是相同的,因此这是明确的复制和粘贴。 - Betlista
3个回答

5

CharSequence 是一个接口,因此您不能直接实例化它。 String 是一个具体的类,它实现了 CharSequence 接口。 StringBuffer 也实现了 CharSequence 接口。

至于为什么 StringBuffer 有两个构造函数,一个接受 String,另一个接受 CharSequence,几乎肯定是因为(根据 Javadoc 中的 Since 行),CharSequence 直到 Java v1.4 才被添加,而 StringBuffer(和 String)在 Java 1.0 中就存在了。


4

CharSequence是一个接口,String实现了它。

这意味着,例如,当您在String上调用.charAt()时,实际上调用的是CharSequence方法的String实现。

CharSequence的javadoc中可以看出,JDK中并没有很多类实现此接口。

至于为什么会有两个构造函数,StringBuffer追溯到Java 1.0,而CharSequence仅出现在1.4中;但是,StringBuilder(您应该使用它,而不是StringBuffer)有两个构造函数(一个带有CharSequence作为参数,另一个带有String作为参数),因此当传递String作为参数时可能会有优化。至于这样的优化可能是什么,那就是“使用源代码,卢克”(tm)。

作为一个未在JDK中实现CharSequence的示例,您可以查看我的一个项目:largetext。请注意,生成PatternMatcher使用CharSequence而不是String作为参数;由于String实现了CharSequence,因此将String作为参数传递是有效的。


1
你的帖子澄清了一点情况,但为什么我们需要charsequence和string参数两者?难道它们之中的一个不足以展示StringBuffer构造函数的行为吗? - Abin Lakhanpal
1
当然,只使用CharSequence构造函数就足够了,但优化是同时拥有两者的完全正当的理由。 - Louis Wasserman
2
不,优化不是我们拥有两者的原因。多态意味着优化实现会在底层自动使用。@Avin,你正确指出我们不应该需要两者。由于String是一个CharSequence,我们可以简单地将一个字符串实例传递给期望一个CharSequence实例的方法。我们之所以拥有这两个是因为早期的Java团队没有彻底考虑这个问题。CharSequence接口是在Java 4(1.4)中添加的,因此已经存在期望一个字符串的签名。 - Basil Bourque
1
@BasilBourque 好的,但是为什么 StringBuilder 这个类,它是从1.5版本开始引入的,也有这两种构造函数呢? - fge
那些对这些与文本相关的类及其扭曲历史感到困惑的人可能会在我的答案中找到有用的 我的图表,该答案是关于Java中CharSequence和String的确切区别的问题。 - Basil Bourque
显示剩余5条评论

0

public StringBuffer(String str) : 构造一个字符串缓冲区,其内容初始化为指定字符串的内容。字符串缓冲区的初始容量为16加上字符串参数的长度。

public StringBuffer(CharSequence seq) : 构造一个包含与指定CharSequence相同字符的字符串缓冲区。字符串缓冲区的初始容量为16加上CharSequence参数的长度。 如果指定的CharSequence的长度小于或等于零,则返回容量为16的空缓冲区。

http://grepcode.com/file/repository.grepcode.com/java/root/jdk/openjdk/6-b14/java/lang/StringBuffer.java#StringBuffer.%3Cinit%3E%28java.lang.String%29


我不确定,但这是源代码所说的。 - Kartic
这就是为什么我不喜欢OpenJDK,谁知道是谁添加了这个注释,而在Oracle JDK中却没有... - Betlista
是的,我努力尝试证明长度可以小于0(可能为-1),但这是不可能的。 - Kartic

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接