【问题标题】:Why does Hashtable use Entry<?,?> internally?为什么 Hashtable 在内部使用 Entry<?,?>?
【发布时间】:2015-10-23 16:36:48
【问题描述】:

这里是Hashtable#get

@SuppressWarnings("unchecked")
public synchronized V get(Object key) {
    Entry<?,?> tab[] = table;
    int hash = key.hashCode();
    int index = (hash & 0x7FFFFFFF) % tab.length;
    for (Entry<?,?> e = tab[index] ; e != null ; e = e.next) {
        if ((e.hash == hash) && e.key.equals(key)) {
            return (V)e.value;
        }
    }
    return null;
}

为什么它使用Entry&lt;?,?&gt; 而不是Entry&lt;K,V&gt;

【问题讨论】:

  • 我的源代码(1.8)说实例变量table也是通配符——private transient Entry&lt;?,?&gt;[] table;

标签: java generics collections


【解决方案1】:

Hashtable 的创建早于 Java 1.5 中使用泛型所做的任何工作,因此这里可能的情况是对泛型进行了改造。

虽然更大的原因可能是table 是一个数组,而泛型和数组不能很好地相处。

如果输入了tableHashtable 中的字段),您将不得不处理大量此类声明...

// Generic array creation! 
Entry<K, V>[] newMap = new Entry<K, V>[newCapacity];

...可能的设计/实现决定是争取兼容性,而不是全面拥抱泛型。

另外请注意,使用通配符创建数组类型不会导致编译时错误,而创建具有具体类型的数组,因为具有未绑定的泛型类型通配符is considered reifiable:

List<?>[] foo = new ArrayList[10]; // perfectly legal but not encouraged
List<String> bar = new ArrayList[10]; // not legal

未来的约定将改为使用HashMap,因为这个特定的实现既是同步的,而且仍然使用许多 1.5 之前的约定。 (如果你想同步,连文档都推荐ConcurrentHashMap。)

【讨论】:

    猜你喜欢
    • 2012-05-30
    • 1970-01-01
    • 2015-02-02
    • 1970-01-01
    • 2017-05-18
    • 2011-11-25
    • 1970-01-01
    • 1970-01-01
    • 2019-05-27
    相关资源
    最近更新 更多