当前位置: 首页 > 面试题库 >

Java中的flyweight字符串什么时候有益?

穆铭晨
2023-03-14
问题内容

我了解Java的String Interning的基本概念,但是我试图弄清楚它发生在哪些情况下,以及我需要自己进行权重加权。

他们在一起告诉我这String s = "foo"是好String s = new String("foo")是坏,但没有提到任何其他情况。

尤其是,如果我解析具有很多重复值的文件(例如csv),那么Java的字符串插入将覆盖我还是我需要自己做点什么?关于字符串实习是否适用于我的其他问题,我已经提出了相互矛盾的建议

完整的答案分为几个部分,因此我在这里总结一下:

默认情况下,java仅实习编译时已知的字符串。
String.intern(String)可以在运行时使用,但效果不是很好,因此它仅适用于数量较少String的,您可以肯定会重复 很多
。对于更大的琴弦,可以使用番石榴进行救援(请参阅ColinD的答案)。


问题答案:

不要在代码中使用String.intern()。至少不会,如果您可能会得到20个或更多不同的字符串。以我的经验,String.intern当您有数百万个字符串时,使用会降低整个应用程序的速度。

为避免String对象重复,只需使用即可HashMap

private final Map<String, String> pool = new HashMap<String, String>();

private void interned(String s) {
  String interned = pool.get(s);
  if (interned != null) {
    return interned;
  pool.put(s, s);
  return s;
}

private void readFile(CsvFile csvFile) {
  for (List<String> row : csvFile) {
    for (int i = 0; i < row.size(); i++) {
      row.set(i, interned(row.get(i)));
      // further process the row
    }
  }
  pool.clear(); // allow the garbage collector to clean up
}

使用该代码,您可以避免一个CSV文件重复字符串。如果需要避免大规模使用,请pool.clear()在另一个地方打电话。



 类似资料:
  • 在Java中,当一个对象没有实时引用时,它就有资格进行垃圾回收。对于字符串,情况并非如此,因为字符串将进入字符串池,而JVM将保持对象活动以供重用。这意味着字符串一旦创建就永远不会被垃圾收集?

  • 问题内容: 我对Java中的StringPool感到困惑。我在阅读Java中的String一章时遇到了这个问题。用外行的术语,请帮助我了解StringPool的实际作用。 问题答案: 打印(即使我们不使用方法:比较字符串的正确方法) 当编译器优化你的字符串文字时,它会看到两者s和t具有相同的值,因此你只需要一个字符串对象。这是安全的,因为在中是不可变的。 结果,两者和都t指向同一个对象,节省了一些

  • (1)重载是多态的集中体现,在类中,要以统一的方式处理不同类型数据的时候,可以用重载。 (2)重写的使用是建立在继承关系上的,子类在继承父类的基础上,增加新的功能,可以用重写。 (3)简单总结: 重载是多样性,重写是增强剂; 目的是提高程序的多样性和健壮性,以适配不同场景使用时,使用重载进行扩展; 目的是在不修改原方法及源代码的基础上对方法进行扩展或增强时,使用重写; 生活例子: 你想吃一碗面,我

  • 据我所知, 可变字符串可以更改,不可变字符串不能更改。 这里我想这样改变字符串的值, 另一种方法是, 在这两种情况下,我都试图改变str的值。谁能告诉我,这两种情况的区别是什么,让我清楚地了解可变和不可变对象。

  • 问题内容: 我正在使用一个返回字节字符串的库,我需要将其转换为字符串。 尽管我不确定有什么区别-如果有的话。 问题答案: 假设使用Python 3(在Python 2中,这种区别的定义不太明确)-字符串是字符序列,即unicode码点;这些是一个抽象概念,不能直接存储在磁盘上。毫无疑问,字节字符串是字节的序列- 可以 存储在磁盘上的东西。它们之间的映射是一种 编码 -其中有很多(并且无限可能)-并

  • 问题内容: 有哪些现实的例子可以理解断言的关键作用? 问题答案: 断言(通过assert关键字)是在Java 1.4中添加的。它们用于验证代码中不变式的正确性。切勿在生产代码中触发它们,并表示存在错误或滥用代码路径。可以在运行时通过命令上的选项将其激活,但默认情况下未启用它们。 一个例子: