首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >正如String.intern()方法的Javadoc中提到的,String最初真的是空的吗?

正如String.intern()方法的Javadoc中提到的,String最初真的是空的吗?
EN

Stack Overflow用户
提问于 2018-04-24 11:19:00
回答 1查看 1.4K关注 0票数 5

下面是String.intern()方法的Javadoc注释:

*返回字符串对象的规范表示形式。

字符串池(最初为空)由类字符串私下维护。

当调用intern方法时,如果池中已经包含了一个与这个字符串对象相等的字符串,则返回来自这个池的字符串。否则,将此字符串对象添加到池中,并返回对此字符串对象的引用。

因此,对于任意两个字符串s和t,s.intern() == t.intern()是真当且仅当s.equals(t)为真。

所有文字字符串和字符串值常量表达式都是内嵌的。字符串文字在Java规范第3.10.5节中定义。“

,但我认为是一些东西改变了jdk-8u102以前的.

请查看下面的示例:

代码语言:javascript
复制
public class Test1 {
    public static void main(String[] args) {
        String s1 = new String(new char[]{'J', 'a', 'v', 'a'});
        String s2 = s1.intern(); 
        System.out.println(s1 == s2);
    }
}

如果您在JDK 7u80 ( JDK 7的最后一个稳定版本)和JDK 8到8u101中运行上述程序,那么输出是:

但是,如果您在JDK 8u102和JDK 9& JDK 10中运行上述程序,则输出是:

为什么intern()方法开始有不同的行为方式?

我检查了发行说明和Javadoc注释,但没有发现与JDK8u102中的intern()方法相关的任何更改。

我查过博客和其他网站,但没有运气。

但是,当我尝试使用其他字符串时,输出没有变化:

代码语言:javascript
复制
public class Test2 {
    public static void main(String[] args) {
        String s3 = new String(new char[]{'U', 'd', 'a', 'y', 'a', 'n'});
        String s4 = s3.intern();
        System.out.println(s3 == s4);
    }
}

上面的程序总是在JDK 7、JDK 8、JDK 9和JDK 10中打印

只有当字符串池表在加载Test1类之前引用“Java”时,才有可能出现这种行为。

s1引用堆上的字符串对象“Java”,s1.intern()返回String对象的引用(因为字符串池已经引用了“Java”)。

这就是为什么s1 == s2返回false的原因。

但是,当加载Test2类时,String表不引用“Udayan”。

s3引用堆上的String对象“Udayan”,s3.intern()将s3引用的String对象添加到String中,并返回相同的引用。这意味着s3和s4引用同一个对象。

这就是为什么s3 == s4返回true的原因。

如果我的观察是正确的,那么这意味着字符串池最初并不是空的。

字符串池最初包含“java”、“java”、“Oracle”和其他字符串对象。

有人能确认一下吗?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2018-04-24 11:24:31

这取决于你认为什么是“最初”。

JVM启动时,字符串池为空。但是,当在加载Test1类之前加载和初始化各种基本JDK类时,其中一些类将Strings添加到String中就不足为奇了。"Java“必须是这些String之一。

JLS没有阻止Java开发人员在更新的JDK版本的类初始化中引入新的String文字。因此,您注意到JDK 7和JDK 8之间的差异并不奇怪。

票数 9
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/50000370

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档