java HashMap如何链接?如何访问所有碰撞值?
Posted
技术标签:
【中文标题】java HashMap如何链接?如何访问所有碰撞值?【英文标题】:How java HashMap does chaining? how to access all collision values? 【发布时间】:2012-01-27 21:49:40 【问题描述】:我在某处读到 HashMap 使用链接来解决冲突。但如果是这样的话。如何访问具有相同键值的所有元素。
例如:
HashMap<Integer, String> hmap = new HashMap<Integer, String>();
hmap.put(1, "1st value");
hmap.put(1, "2nd value");
hmap.put(1, "3rd value");
hmap.put(1, "4th value");
现在,如果我执行 hmap.get(1),它会返回“第 4 个值”
如果它确实像链接一样
键值1“第四值”--->“第三值”--->“第二值”----> “第一价值”
如何获取其他值?
hmap.get(1)
只返回第一个值。
我的第二个问题是,
如果它执行线性链接。如何删除键的任何一个值。假设我想从我的 hashmap 中删除“第 4 个值”,并希望为同一个键保留所有其他值,我该怎么做?
如果我这样做了
hmap.remove(1);
,它删除了整个链。
【问题讨论】:
【参考方案1】:来自HashMap.put(K, V)的文档:
将指定值与此映射中的指定键相关联。如果映射先前包含键的映射,则替换旧值。
您可以做的是将List
作为您的值,例如
HashMap<Integer, List<String>> hmap = new HashMap<Integer, List<String>>();
List<String> list = hmap.get(1);
if (list == null)
list = new ArrayList<String>();
hmap.put(1, list);
list.add("1st value");
list.add("2nd value");
// etc
【讨论】:
【参考方案2】:我认为 HashTable 不允许重复键。你应该阅读这个What happens when a duplicate key is put into a HashMap?
【讨论】:
【参考方案3】:HashMap
不能为同一个键存储多个值。
Chaining 用于解决哈希冲突,即不同键具有相同哈希的情况。所以,这不是关于使用同一个键存储多个值,而是关于键具有相同哈希值的多个值。
可以为同一个键存储多个值的数据结构称为多重映射。不幸的是,JRE 中没有内置的 multimap 实现。
如果您需要多图,您可以维护 List
s 中的 Map
(如 matsev 建议的那样),或使用来自第三方库的现有多图实现,例如 Google Guava。
另请参阅:
Collision resolution【讨论】:
或者换句话说,当两个不同的键散列到同一个散列表槽时会发生冲突。什么是 OP 是多个相同的键。【参考方案4】:您显然正在寻找像 Guava 的 MultiMap 这样的数据结构,它完全可以满足您的需求:每个键具有多个值。
Java 的 HashMap 不进行链接,正如documentation for put(K, V)
明确指出的那样:
public V put(K key, V value)
将指定的值与此映射中的指定键相关联。如果 映射先前包含键的映射,旧值是 换了。
【讨论】:
实际上,它确实做哈希链。但是链接并不是要在映射中存储同一个键的多个副本。它是关于处理 不同 键映射到哈希表中的同一槽的情况。这就是碰撞。【参考方案5】:如果您将现有键存储在 HashMap 中,那么它将用新值覆盖旧值,而 put() 将返回旧值
System.out.println(hmap.put("1",1st value));
System.out.println(hmap); // o/p "1st value"
【讨论】:
以上是关于java HashMap如何链接?如何访问所有碰撞值?的主要内容,如果未能解决你的问题,请参考以下文章