为什么Java在Map中没有putIfAbsent(key,supplier)方法?

时间:2014-11-25 12:56:30

标签: java collections map

我最近发现自己想在java.util.Map中使用一个版本的putIfAbsent(...),你可以提供某种工厂方法,以便在它尚未存在时实例化它。这样可以简化很多代码。

这是我修改过的界面:

import java.util.Map;
import java.util.function.Supplier;

/**
 * Extension of the Map Interface for a different approach on having putIfAbsent
 * 
 * @author Martin Braun
 */
public interface SupplierMap<K, V> extends Map<K, V> {

    public default V putIfAbsent(K key, Supplier<V> supplier) {
        V value = this.get(key);
        if(value == null) {
            this.put(key, value = supplier.get());
        }
        return value;
    }

}

现在我的问题: 还有另一种(更简单的)方法吗?或者我只是忽略了Java API中的某些内容?

2 个答案:

答案 0 :(得分:21)

不是computeIfAbsent你想要什么?

  

如果指定的键尚未与值关联(或者是   映射到null),尝试使用给定的映射计算其值   函数并将其输入此映射,除非为null。

实施类似于:

if (map.get(key) == null) {
    V newValue = mappingFunction.apply(key);
    if (newValue != null) {
         map.put(key, newValue);
    }
}

所以它并不完全是您发布的Supplier<V>签名,但接近于此。在映射函数中使用key作为参数肯定是有道理的。

答案 1 :(得分:0)

computeIfAbsent 不是1:1替代 putIfAbsent ,因为返回值的约束不匹配。创建新条目时, putIfAbsent 返回,而 computeIfAbsent 始终返回分配的值。

上面建议的默认实现,先调用 get ,然后 put 即可,但是它需要在地图中进行两次查找,这破坏了表演者的想法。就地替换。