首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >String.intern()的返回解释

String.intern()的返回解释
EN

Stack Overflow用户
提问于 2019-03-13 06:50:48
回答 3查看 2K关注 0票数 20

考虑:

代码语言:javascript
复制
String s1 = new StringBuilder("Cattie").append(" & Doggie").toString();
System.out.println(s1.intern() == s1); // true why?
System.out.println(s1 == "Cattie & Doggie"); // true another why?

String s2 = new StringBuilder("ja").append("va").toString();
System.out.println(s2.intern() == s2); // false

String s3 = new String("Cattie & Doggie");
System.out.println(s3.intern() == s3); // false
System.out.println(s3 == "Cattie & Doggie"); // false

我感到困惑的是,为什么返回值 of String.intern()会产生不同的结果:

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

特别是在这两次测试之后:

代码语言:javascript
复制
assertFalse("new String() should create a new instance", new String("jav") == "jav");
assertFalse("new StringBuilder() should create a new instance",
    new StringBuilder("jav").toString() == "jav");

我曾经读过一篇文章,谈到一些special strings在其他事情之前就被拘留了,但现在真的很模糊了。

如果有一些字符串pre-interned,有什么方法可以获得它们的列表吗?我只是好奇他们能成为什么。

已更新

感谢@Eran和@Slaw的帮助,我终于可以为输出解释刚才发生了什么

代码语言:javascript
复制
true
true
false
false
false
  1. 由于池中不存在"Cattie & Doggie",所以s1.intern()将把当前的对象引用放到池中并返回自己,因此s1.intern() == s1
  2. "Cattie & Doggie"现在已经在池中了,所以字符串文本"Cattie & Doggie"将只使用池中的引用,实际上是s1,所以我们又有了true
  3. new StringBuilder().toString()将在"java"已经在池中时创建一个新实例,然后在调用s2.intern()时返回池中的引用,因此s2.intern() != s2和我们有false
  4. new String()也会返回一个新的实例,但是当我们尝试s3.intern()时,它将返回池中先前存储的引用,这实际上是s1,所以是s3.intern() != s3,我们有false
  5. 正如前面讨论的#2一样,字符串文本"Cattie & Doggie"将返回存储在池中的引用(实际上是s1),因此s3 != "Cattie & Doggie"和我们又有了false

感谢@Sunny提供了一个获得所有interned字符串的技巧。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2019-03-13 06:54:39

只有当字符串池在调用之前不包含值为"java“的s2.intern()时,s2才会返回s2引用的实例。在执行代码之前,JDK类会实习生一些String。"java“一定是其中之一。因此,s2.intern()返回以前的实习生实例,而不是s2

另一方面,JDK类没有实习生任何值等于“String & Doggie”的s1.intern(),因此s1.intern()返回s1

我不知道任何被拘留前的字符串列表。这样的列表很可能被认为是实现细节,在不同的JDK实现和JDK版本上可能有所不同,不应该依赖。

票数 29
EN

Stack Overflow用户

发布于 2019-03-13 07:01:07

当对String对象调用intern()方法时,它会在池中查找此字符串对象包含的字符串,如果在池中找到该字符串,则返回池中的字符串。否则,将此字符串对象添加到池中,并返回对此字符串对象的引用。

所以java字符串必须已经在池中了。因此,这是虚假的。

您可以在池中打印所有字符串。

如何打印整个字符串池?

如果您正在使用示例 openjdk,下面是一个获取所有字符串的。

票数 3
EN

Stack Overflow用户

发布于 2019-03-13 07:05:06

字符串文本(那些像“字符串”那样硬编码的文本)已经由编译器为您提供了内嵌。但是那些以编程方式获得的字符串不是,并且只有在使用.intern()方法时才会被嵌入。

通常您不会手动执行字符串,除非您知道您将在内存中存储大量重复字符串,这样就可以节省大量内存。

这一点在这里解释:什么是Java字符串实习?

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

https://stackoverflow.com/questions/55135968

复制
相关文章

相似问题

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