JDK 1.8 Map 新增方法

getOrDefault

V getOrDefault(Object key, V defaultValue)

当 Map 中不包含指定的 key 时,返回默认值。

Map<String, String> map = new HashMap<>();
map.put("k1", null);
map.put("k2", "a");

String v1 = map.getOrDefault("k1", "v1");
String v2 = map.getOrDefault("k2", "v2");
String v3 = map.getOrDefault("k3", "v3");

System.out.println(v1);
System.out.println(v2);
System.out.println(v3);
null
a
v3

默认实现

V v;
return (((v = get(key)) != null) || containsKey(key)) 
	? v : defaultValue;

remove

boolean remove(Object key, Object value)

仅当指定的 key 关联到指定的 value 时,才删除指定的项,删除成功返回 true。

Map<String, String> map = new HashMap<>();
map.put("k1", null);
map.put("k2", "a");
map.put("k3", "b");
map.put("k4", "");

System.out.println(map);

// value 不同,失败
boolean b1 = map.remove("k1", "a");
// value 不同,失败
boolean b2 = map.remove("k2", "b");
// value 相同,成功
boolean b3 = map.remove("k3", "b");

System.out.println(b1);
System.out.println(b2);
System.out.println(b3);

System.out.println(map);
{k1=null, k2=a, k3=b, k4=}
false
false
true
{k1=null, k2=a, k4=}

默认实现等价于

// 包含 key,且 value 相等
if (map.containsKey(key) && Objects.equals(map.get(key), value)) {
    map.remove(key);
    return true;
} else
    return false;

putIfAbsent

V putIfAbsent(K key, V value)

当指定的 key 没有对应的 value(或对应的 value 为 null )时,执行 put 操作并返回 null,否则只返回当前的 value(不执行 put)。

Map<String, String> map = new HashMap<>();
// 没有与 key 对应的 value,返回 null
String r1 = map.putIfAbsent("k", "a");
System.out.println(map + " " + r1);

// key 已经有对应的值 a 了,没有执行 put(k, b),且返回了当前值 a
String r2 = map.putIfAbsent("k", "b");
System.out.println(map + " " + r2);
{k=a} null
{k=a} a

默认实现等价于

 V v = map.get(key);
 if (v == null)
     v = map.put(key, value);

 return v;

forEach

void forEach(BiConsumer<? super K, ? super V> action)

使用所有的键值对特定的操作。

Map<String, String> map = new HashMap<>();
map.put("k1", null);
map.put("k2", "a");
map.put("k3", "b");
map.put("k4", "");

map.forEach((k, v) -> System.out.println(k + " " + v));
k1 null
k2 a
k3 b
k4 

默认实现等价于

for (Map.Entry<K, V> entry : map.entrySet())
     action.accept(entry.getKey(), entry.getValue());

replace

replace(key, value)

V replace(K key, V value)

若指定的 key 存在,则用新值替换旧值。替换成功返回旧值,否则返回 null。

Map<String, String> map = new HashMap<>();

// 没有与 key 对应的 value,没有替换,返回 null
String r1 = map.replace("k", "a");
System.out.println(map + " " + r1);

map.put("k", null);
System.out.println(map);

// key 已经有对应的值 null 了,替换成功,且返回了旧值 null
String r2 = map.replace("k", "b");
System.out.println(map + " " + r2);

map.put("k", "a");
System.out.println(map);

// key 已经有对应的值 a 了,替换成功,且返回了旧值 a
String r3 = map.replace("k", "c");
System.out.println(map + " " + r3);
{} null
{k=null}
{k=b} null
{k=a}
{k=c} a

默认实现等价于

if (map.containsKey(key)) {
    return map.put(key, value);
} else
    return null;

replace(key, oldValue, newValue)

boolean replace(K key, V oldValue, V newValue)

只有当指定的 key 存在,且关联的值等于 oldValue 时,才用新值 newValue 替换旧值,替换成功返回 true。

Map<String, String> map = new HashMap<>();
map.put("k1", "a");
map.put("k2", "b");
System.out.println(map);

// k3 不存在,替换失败
boolean r1 = map.replace("k3", "c", "ccc");
System.out.println(map + " " + r1);

// k1 存在,但值不等于 aa,替换失败
boolean r2 = map.replace("k1", "aa", "aaa");
System.out.println(map + " " + r2);

// k2 存在,且值等于 b,替换成功
boolean r3 = map.replace("k2", "b", "bbb");
System.out.println(map + " " + r3);
{k1=a, k2=b}
{k1=a, k2=b} false
{k1=a, k2=b} false
{k1=a, k2=bbb} true

默认实现等价于

// 存在key,且value相等
if (map.containsKey(key) && Objects.equals(map.get(key), oldValue)) {
    map.put(key, newValue);
    return true;
} else
    return false;

replaceAll

void replaceAll(BiFunction<? super K, ? super V, ? extends V> function)

使用传入的 function 重新计算所有的 value

Map<String, String> map = new HashMap<>();
map.put("k1", null);
map.put("k2", "a");
map.put("k3", "b");
map.put("k4", "");

System.out.println(map);

map.replaceAll((k, v)-> k + v);

System.out.println(map);
{k1=null, k2=a, k3=b, k4=}
{k1=k1null, k2=k2a, k3=k3b, k4=k4}

默认实现等价于

for (Map.Entry<K, V> entry : map.entrySet())
    entry.setValue(function.apply(entry.getKey(), entry.getValue()));

computeIfAbsent

V computeIfAbsent(K key, Function<? super K, ? extends V> mappingFunction)
// mappingFunction 的参数是 key,返回值是 value

如果指定的 key 不存在(或关联的 value 为 null),则使用给定的 function 计算 value 并执行 put(只有计算出的 value 不为 null 才 put),总是返回当前的最新值(已存在的或刚刚计算出来的)。最常见的用法是构造一个新对象作为初始映射值:map.computeIfAbsent(key, k -> new Value(f(k)));

或者实现一个多值(multi-value)Map, Map<K,Collection<V>>,支持每个键多个值:map.computeIfAbsent(key, k -> new HashSet<V>()).add(v);

Map<String, String> map = new HashMap<>();
map.put("k2", null);
map.put("k3", "c");

System.out.println(map);

// k1 不存在,执行 put
String v1 = map.computeIfAbsent("k1", (k) -> k + k);
// k2 存在,但值为null,执行 put
String v2 = map.computeIfAbsent("k2", (k) -> k + k);
// k3 存在,但值不为null,不执行 put
String v3 = map.computeIfAbsent("k3", (k) -> k + k);
// k4 不存在,但计算结果为 null,不执行 put
String v4 = map.computeIfAbsent("k4", (k) -> null);

System.out.println(v1);
System.out.println(v2);
System.out.println(v3);
System.out.println(v4);

System.out.println(map);
{k2=null, k3=c}
k1k1
k2k2
c
null
{k1=k1k1, k2=k2k2, k3=c}

实现一个ArrayListMultiMap

public class ArrayListMultiMap<K, V> {

    private final Map<K, ArrayList<V>> map;

    public ArrayListMultiMap() {
        map = new HashMap<>();
    }

    public void put(K key, V value) {
        map.computeIfAbsent(key, (k) -> new ArrayList<>()).add(value);
    }

    public ArrayList<V> get(K key) {
        return map.get(key);
    }

    @Override
    public String toString() {
        return "ArrayListMultiMap{" +
                "map=" + map +
                '}';
    }

    public static void main(String[] args) {
        ArrayListMultiMap<String, String> multiMap = new ArrayListMultiMap<>();
        multiMap.put("k1", "a");
        multiMap.put("k1", "b");
        multiMap.put("k1", "a");
        multiMap.put("k1", "c");
        multiMap.put("k2", "aa");
        multiMap.put("k2", "bb");
        System.out.println(multiMap);

    }
}
ArrayListMultiMap{map={k1=[a, b, a, c], k2=[aa, bb]}}

默认实现

default V computeIfAbsent(K key,
                          Function<? super K, ? extends V> mappingFunction) {
    Objects.requireNonNull(mappingFunction);
    V v;
    // key 没有关联的 value
    if ((v = get(key)) == null) {
        V newValue;
        // 计算出的 value 不为 null
        if ((newValue = mappingFunction.apply(key)) != null) {
            put(key, newValue);
            return newValue;
        }
    }

    return v;
}

computeIfPresent

V computeIfPresent(K key, BiFunction<? super K, ? super V, ? extends V> remappingFunction)
// remappingFunction 的参数是(key, oldValue),返回值是 newValue

仅当指定 key 关联的 value 存在且非 null 时,使用给定的 function 计算新的 value。如果 function 的返回值为 null,则执行删除,返回最新的值或 null(key 不存在或 value 为 null ,或 function 的结果为 null 时)。

Map<String, String> map = new HashMap<>();
map.put("k1", "a");
map.put("k3", null);
map.put("k4", "d");

System.out.println(map);

// k1 存在且值不为 null,执行 put
String v1 = map.computeIfPresent("k1", (k, v) -> k + v);
// k2 不存在,不执行 put
String v2 = map.computeIfPresent("k2", (k, v) -> k + v);
// k3 存在,但值为null,不执行 put
String v3 = map.computeIfPresent("k3", (k, v) -> k + v);
// k4 存在,但计算结果为 null,不执行 put
String v4 = map.computeIfPresent("k4", (k, v) -> null);

System.out.println(v1);
System.out.println(v2);
System.out.println(v3);
System.out.println(v4);

System.out.println(map);
{k1=a, k3=null, k4=d}
k1a
null
null
null
{k1=k1a, k3=null}

默认实现

default V computeIfPresent(K key, BiFunction<? super K, ? super V, ? extends V> remappingFunction) {
    Objects.requireNonNull(remappingFunction);
    V oldValue;
    // key 关联的 value 存在且不为 null
    if ((oldValue = get(key)) != null) {
        V newValue = remappingFunction.apply(key, oldValue);
        // 计算结果不为 null,执行 put
        if (newValue != null) {
            put(key, newValue);
            return newValue;
        // 计算结果为 null,执行删除
        } else {
            remove(key);
            return null;
        }
    } else {
        return null;
    }
}

compute

V compute(K key, BiFunction<? super K, ? super V, ? extends V> remappingFunction)
// remappingFunction 的参数是(key, oldValue),返回值是 newValue

使用 function 计算 value,若 value 不为 null,执行 put,否则执行删除。返回最新的值,或 null(function 返回值为 null 时)。

Map<String, String> map = new HashMap<>();
map.put("k1", "a");
map.put("k3", null);
map.put("k4", "d");

System.out.println(map);

// function 返回值不为 null,执行 put
String v1 = map.compute("k1", (k, v) -> k + v);
// function 返回值不为 null,执行 put
String v2 = map.compute("k2", (k, v) -> k + v);
// function 返回值不为 null,执行 put
String v3 = map.compute("k3", (k, v) -> k + v);
// function 返回值为 null,执行删除
String v4 = map.compute("k4", (k, v) -> null);

System.out.println(v1);
System.out.println(v2);
System.out.println(v3);
System.out.println(v4);

System.out.println(map);
{k1=a, k3=null, k4=d}
k1a
k2null
k3null
null
{k1=k1a, k2=k2null, k3=k3null}

默认实现

default V compute(K key, BiFunction<? super K, ? super V, ? extends V> remappingFunction) {
    Objects.requireNonNull(remappingFunction);
    V oldValue = get(key);

    // 计算新值
    V newValue = remappingFunction.apply(key, oldValue);
    // 新值为 null
    if (newValue == null) {
        // delete mapping 删除
        if (oldValue != null || containsKey(key)) {
            // something to remove
            remove(key);
            return null;
        } else {
            // nothing to do. Leave things as they were.
            return null;
        }
    } else {
        // 新值不为 null 插入或更新
        // add or replace old mapping
        put(key, newValue);
        return newValue;
    }
}

merge

V merge(K key, V value, BiFunction<? super V, ? super V, ? extends V> remappingFunction)
// remappingFunction 的参数(oldValue, paramValue),返回值 newValue

如果指定的 key 不存在(或关联的 value 为 null),则使用给定的 value 执行 put。否则使用给定的 function 计算 value 并执行 put(function 返回值 为 null 时会执行删除)。当需要组合同一个 key 的多个 value 时很有用,比如创建或追加 msg 到 value:map.merge(key, msg, String::concat)

Map<String, String> map = new HashMap<>();
map.put("k2", null);
map.put("k3", "c");
map.put("k4", "d");

System.out.println(map);

// k1 不存在,执行 put
String v1 = map.merge("k1", "a", String::concat);
// k2 存在但值为 null,执行 put
String v2 = map.merge("k2", "b", String::concat);
// k3 存在,执行 merge
String v3 = map.merge("k3", "-c", String::concat);
// k4 存在,但 function 返回值为 null,执行 删除
String v4 = map.merge("k4", "c", (oldValue, value) -> null);


System.out.println(v1);
System.out.println(v2);
System.out.println(v3);
System.out.println(v4);

System.out.println(map);
{k2=null, k3=c, k4=d}
a
b
c-c
null
{k1=a, k2=b, k3=c-c}

默认实现

default V merge(K key, V value, BiFunction<? super V, ? super V, ? extends V> remappingFunction) {
    Objects.requireNonNull(remappingFunction);
    // 指定的 value 不能为 null
    Objects.requireNonNull(value);
    V oldValue = get(key);
    // 旧值不存在,则使用给定 value 执行 put
    // 旧值存在,则使用 Function 计算新值
    V newValue = (oldValue == null) ? value : remappingFunction.apply(oldValue, value);
    // Function 返回值为 null,执行删除
    if(newValue == null) {
        remove(key);
    } else {
        put(key, newValue);
    }
    return newValue;
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值