[英]Simple HashMap remove function doesn't update the map entries
我正在尝试实现一个简单的哈希映射,其中映射的每个条目都表示为一个Node
单链表,并且我有一个条目数组,例如Node[] nodes
:
static final class Node {
int key;
int value;
Node next;
int hash;
Node(int key, int value, Node next, int hash) {
this.key = key;
this.value = value;
this.next = next;
this.hash = hash;
}
}
这里是remove方法,它首先尝试在HashMap中定位key的索引位置,然后线性扫描这个entry中的每个节点,并移除map中匹配的key:
public void remove(int key) {
int hash = computeHash(key);
Node node = nodes[hash];
if (node == null) {
return;
}
Node prev = null;
while (node.key != key && node.next != null) {
prev = node;
node = node.next;
}
if (node.key == key) {
if (prev != null) {
prev.next = node.next;
} else if (prev == null) {
node = node.next;
} else {
node = null;
}
size--;
}
}
它不会使匹配的nodes
从外部节点中删除,只有引用的局部变量受到影响。 由于我有对节点的引用,我想从nodes
中删除它(如果有匹配的键),拥有它的地址并尝试将其尊重为null
,但它是无效的。 我很高兴听到一些解释为什么这段代码不起作用。
我有一个像这样的简单测试:
MyHashMap map = new MyHashMap();
map.put(1, 1);
map.put(2, 1);
map.remove(1);
System.out.println(map.get(1)); // still returns 1
您的局部变量node
是nodes[hash]
的副本。 分配给副本不会更改原件。 您需要更改代码以更新原始代码。 而且您不需要检查node.next
是否等于null
:没关系,如果它是null
您将分配null
,这正是您想要的。
if (node.key == key) {
if (prev != null) {
prev.next = node.next;
} else {
nodes[hash] = node.next;
}
size--;
}
检查 node.next 不等于 null 是错误的。 您不应该关心下一个元素,永远不会引用已删除元素中的下一个元素。 HashMap 的源代码是:
if (node == p)
tab[index] = node.next;
else
p.next = node.next;
++modCount;
--size;
'p' 是你的 'prev' 的方法。HashMap 将值分配给这个散列中的第一个元素。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.