【问题标题】:How much memory does a Hashtable use?Hashtable 使用多少内存?
【发布时间】:2010-11-28 08:30:35
【问题描述】:

在Java中,如果我创建一个Hashtable<K, V>并在其中放入N个元素,它会占用多少内存?如果它依赖于实现,那么什么是好的“猜测”?

【问题讨论】:

  • 它可能会被你的键和值对象的大小所支配(除了小地图)。
  • 我已经添加了一个精确的计算,尽管它可能会因虚拟机而异。这并不总是正确的。对于非常小的键和值(例如,对于原语的包装器对象),Entry 对象的大小可能会支配 hashmap/hashtable 的大小(在内部它们是相同的)。如果多个值是对同一对象实例的引用,也会发生这种情况。如果您使用大量原始对象作为键或值,请查看 Trove 库。为此,它更快,内存效率更高。

标签: java hashtable memory-management


【解决方案1】:

编辑; 天哪,我是个白痴,我提供了 HashMap 的信息,而不是 HashTable。但是,在检查后,出于内存目的,实现是相同的。

这取决于您的 VM 的内部内存设置(项目打包、32 位或 64 位指针以及字对齐/大小),Java 未指定。

关于估计内存使用的基本信息可以在here找到。

你可以这样估计:

  • 在 32 位 VM 上,指针为 4 个字节,在 64 位 VM 上,为 8 个字节。
  • 对象开销是 8 个字节的内存(对于空对象,不包含任何内容)
  • 对象被填充为 8 字节的倍数 (ugh)。
  • 每个 hashmap 都有一个小的固定开销:一个浮点数,3 个整数,加上对象开销。
  • 有一个插槽数组,其中一些将有条目,其中一些将保留给新的。已填充插槽与总插槽的比率不超过构造函数中指定的负载因子。
  • slot 数组需要一个对象开销,加上一个 int 的大小,加上每个 slot 的一个指针,以指示存储的对象。
  • 槽数通常是存储映射数的 1.3 到 2 倍,默认加载因子为 0.75,但可能会小于此值,具体取决于哈希冲突。
  • 每个存储的映射都需要一个条目对象。这需要一个对象开销,3 个指针,加上存储的键和值对象,再加上一个整数。

所以,把它放在一起(对于 32/64 位 Sun HotSpot JVM): HashMap 需要 24 字节(本身,原始字段)+ 12 字节(槽数组常量)+ 每个槽 4 或 8 字节 + 每个条目 24/40 字节 + 键对象大小 + 值对象大小 + 将每个对象填充为 8 字节的倍数

或者,大致(最多默认设置,不保证准确):

  • 在 32 位 JVM 上:36 字节 + 32 字节/映射 + 键和值
  • 在 64 位 JVM 上:36 字节 + 56 字节/映射 + 键和值

注意:这需要更多检查,它可能需要 12 个字节用于 64 位 VM 上的对象开销。 我不确定空值——空值的指针可能会以某种方式被压缩。

【讨论】:

    【解决方案2】:

    很难估计。我会先读这个: http://www.codeinstructions.com/2008/12/java-objects-memory-structure.html

    只要用sunjdk工具算出K、V和的大小

    jmap -histo [pid]

    num #instances #bytes 类名

    1: 126170 19671768 MyKClass

    2: 126170 14392544 我的VClass

    3:1 200000 MyHashtable

    如果您不需要同步,您可能还想使用 HashMap 而不是 Hashtable。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-09
      • 2011-04-17
      • 2015-12-03
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多