在插入哈希表时,是否总是需要检查是否存在与要插入的键相对应的空值?
例如,如果我想使用散列图来跟踪字符在单词中出现的次数,我是否总是必须这样做:
if(hashMap.containsKey(ch)){
hashMap.replace(ch, 1+hashMap.get(ch));
}
else{
hashMap.put(ch, 1);
}
或者有可以为我处理此事的功能吗?
答案 0 :(得分:17)
使用merge
。
hashMap.merge(ch, 1, Math::addExact);
或使用方法参考:
ch
1
)尚未与某个值关联或与null关联,请将其与给定的非null值(在这种情况下为(left, right) -> left + right
)关联。 Map
的结果替换关联的值。 答案 1 :(得分:12)
您不必。 merge
有一个hashMap.merge(ch, 1, (oldVal, newVal) -> oldVal + newVal);
方法,可用于更新值:
hashMap
这是什么:
ch
还没有ch
键,则添加一个新条目,其中以1
作为键,hashMap
作为值ch
已经具有一个以(oldVal, newVal) -> oldVal + newVal
作为键的条目,那么将调用最后一个函数来计算更新值。在这种情况下,Map.compute
只需将旧值添加到新值。如Andy's comment中所述,您也可以使用int newValue = hashMap.compute(ch,
(key, existingVal) -> (existingVal == null) ? 1 : existingVal + 1);
:
>df1
V1 V2 V3 V4 V5
a abc|ccc|ggg ttt|ccc|shg yyy|lmn|trs abc|ggt|hgy
b atc|cjc|ggg ttt|ccc|shg abc|lmn|trs abc|opq|sss
c auc|chc|ggg abc|ccc|shg gtc|lmn|trs hyt|lki|ddd
d aoc|cfc|ggg ttt|ccc|shg yyy|lmn|trs rmn|wde|tre
答案 2 :(得分:1)
只需清楚一点,您不必区分键是否已存在于地图中。换句话说,可以在示例中使用replace
,而不是在示例中使用put
。
当然,您确实需要处理是否具有需要包含在更新值中的先前值。正如其他人指出的那样,您可以使用merge
或compute
方法。
但是,如果您有理由更愿意坚持使用put
,则这里有一些有关如何构造代码的想法。
在您的原始代码中,
if(hashMap.containsKey(ch)){
hashMap.replace(ch, 1+hashMap.get(ch));
}
else{
hashMap.put(ch, 1);
}
您调用containsKey
和get
,它们实际上都进行查找。为什么要两次查询?
Integer count = hashMap.get(ch);
if(count != null){
hashMap.replace(ch, 1+count);
}
else{
hashMap.put(ch, 1);
}
除了在一种情况下使用replace
,在另一种情况下使用put
,您也可以很容易地在两种情况下使用put
。您可以结合两种情况:
Integer count = hashMap.get(ch);
if (count == null) {
count = 0;
}
hashMap.put(ch, count + 1);
我发现这种模式非常有用,而且它的作用很大(至少在我正在研究的应用程序中)。这是我对此的思考方式:
// Get the current value.
Integer count = hashMap.get(ch);
if (count == null) {
// Business logic for initial value.
count = 0;
}
// Compute the new value (might be a bunch of business logic).
count++;
// Put the new value back.
hashMap.put(ch, count);