为什么 EnumSet 使用 RegularEnumSet 和 JumboEnumSet 来实现不同的大小。它如何影响性能?

Pra*_*eek 2 java collections set enumset

在探索 Java EnumSet 时,我遇到了两个包私有类,

  1. 正则枚举集
  2. 巨型枚举集

来自 EnumSet 来源:

if (universe.length <= 64)
   return new RegularEnumSet<>(elementType, universe);
else
   return new JumboEnumSet<>(elementType, universe);
Run Code Online (Sandbox Code Playgroud)

RegularEnumSet构造函数也如下所示:

RegularEnumSet(Class<E>elementType, Enum[] universe) {
    super(elementType, universe);
}
Run Code Online (Sandbox Code Playgroud)

而在JumboEnumSet构造函数的情况下是:

JumboEnumSet(Class<E>elementType, Enum[] universe) {
   super(elementType, universe);
   elements = new long[(universe.length + 63) >>> 6];
}
Run Code Online (Sandbox Code Playgroud)

所以我的疑问是:

  • 为什么它根据大小使用不同的 EnumSet。它如何影响性能?

  • 使用元素数组的 JumboEnumSet 背后的逻辑是什么?

rua*_*akh 7

  • RegularEnumSet使用单个long作为其位数组,因此它仅保存 64 位,因此它只能跟踪最多 64 个枚举值的存在或不存在。
  • JumboEnumSet使用 a long[],因此它可以保存任意多个位,因此它可以跟踪任意多个枚举值的存在或不存在。

RegularEnumSet性能稍好一些,因为它的间接性要少一些(它将所有数据存储在对象内,而不必检索单独的数组来查找其数据),位操作要少一些(它不必查找数组索引)等(我不知道这些东西在实践中有多重要,但我确信如果没有合理的理由,他们就不会实现这种方法。)