我已经看过很多原始的例子,描述了String intern()的工作原理,但是我还没有看到一个可以从中受益的真实用例。
我能想到的唯一情况是拥有一个接收大量请求的Web服务,由于僵化的架构,每个请求都非常相似。通过intern()在这种情况下使用请求字段名称,可以显着减少内存消耗。
任何人都可以提供在生产环境中使用intern()并取得巨大成功的示例吗?也许是一个流行的开源产品中的一个例子?
编辑:我指的是手动实习,而不是字符串文字的保证实习等。
答案 0 :(得分:21)
如果您的N
个字符串只能K
个不同的值,而N
远远超过K
,则实习可能会非常有用。现在,您不会将N
个字符串存储在内存中,而只会存储K
。
例如,您可能有ID
类型,其中包含5位数字。因此,只能有10^5
个不同的值。假设您现在正在解析一个包含许多对ID
值的引用/交叉引用的大型文档。假设这个文档总共有10^9
个引用(显然在文档的其他部分重复了一些引用)。
在这种情况下N = 10^9
和K = 10^5
。如果您没有实习字符串,则将10^9
字符串存储在内存中,其中许多字符串为equals
(Pigeonhole Principle}。如果您intern()
解析文档时获得的ID
字符串,并且您没有保留对从文档中读取的未处理字符串的任何引用(因此它们可以被垃圾收集),那么你永远不需要在内存中存储超过10^5
个字符串。
答案 1 :(得分:1)
不是一个完整的答案,而是额外的思考(found here):
因此,在这种情况下的主要好处是使用
==
运算符来内化字符串比使用equals()
方法[对于非内化字符串]要快得多。因此,如果您要将字符串比较一次或三次,请使用intern()
方法。
答案 2 :(得分:1)
我们有一个生产系统,一次处理数百万条数据,其中许多都有字符串字段。我们应已经实习字符串,但有一个错误意味着我们没有。通过修复错误,我们避免了必须进行非常昂贵的(至少6位数,可能是7位)服务器升级。
答案 3 :(得分:1)
实习将有益的示例涉及大量字符串,其中:
典型示例涉及将文本拆分/解析为符号(单词,标识符,URI),然后将这些符号附加到长期数据结构中。 XML处理,编程语言编译和RDF / OWL三重存储作为实习可能是有益的应用而浮现在脑海中。
但实习并非没有问题,特别是如果事实证明上述假设不正确:
最后,通过增加需要跟踪和复制的对象数量,以及增加需要处理的弱引用数量,实现潜在会增加GC开销。这种间接费用的增加必须与有效实习导致的GC费用减少相平衡。
答案 4 :(得分:0)
从不,永远,对用户提供的数据使用实习生,因为这可能导致拒绝服务攻击(因为intern()ed字符串永远不会被释放)。您可以对用户提供的字符串进行验证,但是您再次完成了intern()所需的大部分工作。