前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >LinkedMultiValueMap源码解析

LinkedMultiValueMap源码解析

原创
作者头像
HLee
修改2021-09-24 15:08:56
5600
修改2021-09-24 15:08:56
举报
文章被收录于专栏:房东的猫房东的猫

LinkedMultiValueMap源码

类路径: org.springframework.util.MultiValueMap

代码语言:javascript
复制
public interface MultiValueMap<K, V> extends Map<K, List<V>> {
    @Nullable
    V getFirst(K var1);

    void add(K var1, @Nullable V var2);

    void addAll(K var1, List<? extends V> var2);

    void addAll(MultiValueMap<K, V> var1);

    void set(K var1, @Nullable V var2);

    void setAll(Map<K, V> var1);

    Map<K, V> toSingleValueMap();
}

发现它的类型就是继承自Map,只不过在它的基础上做了一层封装,便于后续的管理调用,再来看看LinkedMultiValueMap的实现:

代码语言:javascript
复制
public class LinkedMultiValueMap<K, V> implements MultiValueMap<K, V>, Serializable, Cloneable {
    private static final long serialVersionUID = 3801124242820219131L;
    private final Map<K, List<V>> targetMap;

    public LinkedMultiValueMap() {
        this.targetMap = new LinkedHashMap();
    }

    public LinkedMultiValueMap(int initialCapacity) {
        this.targetMap = new LinkedHashMap(initialCapacity);
    }

    public LinkedMultiValueMap(Map<K, List<V>> otherMap) {
        this.targetMap = new LinkedHashMap(otherMap);
    }

    @Nullable
    public V getFirst(K key) {
        List<V> values = (List)this.targetMap.get(key);
        return values != null ? values.get(0) : null;
    }

    public void add(K key, @Nullable V value) {
        List<V> values = (List)this.targetMap.computeIfAbsent(key, (k) -> {
            return new LinkedList();
        });
        values.add(value);
    }

    public void addAll(K key, List<? extends V> values) {
        List<V> currentValues = (List)this.targetMap.computeIfAbsent(key, (k) -> {
            return new LinkedList();
        });
        currentValues.addAll(values);
    }

    public void addAll(MultiValueMap<K, V> values) {
        Iterator var2 = values.entrySet().iterator();

        while(var2.hasNext()) {
            Entry<K, List<V>> entry = (Entry)var2.next();
            this.addAll(entry.getKey(), (List)entry.getValue());
        }

    }

    public void set(K key, @Nullable V value) {
        List<V> values = new LinkedList();
        values.add(value);
        this.targetMap.put(key, values);
    }

    public void setAll(Map<K, V> values) {
        values.forEach(this::set);
    }

    public Map<K, V> toSingleValueMap() {
        LinkedHashMap<K, V> singleValueMap = new LinkedHashMap(this.targetMap.size());
        this.targetMap.forEach((key, value) -> {
            singleValueMap.put(key, value.get(0));
        });
        return singleValueMap;
    }

    public int size() {
        return this.targetMap.size();
    }

    public boolean isEmpty() {
        return this.targetMap.isEmpty();
    }

    public boolean containsKey(Object key) {
        return this.targetMap.containsKey(key);
    }

    public boolean containsValue(Object value) {
        return this.targetMap.containsValue(value);
    }

    @Nullable
    public List<V> get(Object key) {
        return (List)this.targetMap.get(key);
    }

    @Nullable
    public List<V> put(K key, List<V> value) {
        return (List)this.targetMap.put(key, value);
    }

    @Nullable
    public List<V> remove(Object key) {
        return (List)this.targetMap.remove(key);
    }

    public void putAll(Map<? extends K, ? extends List<V>> map) {
        this.targetMap.putAll(map);
    }

    public void clear() {
        this.targetMap.clear();
    }

    public Set<K> keySet() {
        return this.targetMap.keySet();
    }

    public Collection<List<V>> values() {
        return this.targetMap.values();
    }

    public Set<Entry<K, List<V>>> entrySet() {
        return this.targetMap.entrySet();
    }

    public LinkedMultiValueMap<K, V> deepCopy() {
        LinkedMultiValueMap<K, V> copy = new LinkedMultiValueMap(this.targetMap.size());
        this.targetMap.forEach((key, value) -> {
            copy.put(key, (List)(new LinkedList(value)));
        });
        return copy;
    }

    public LinkedMultiValueMap<K, V> clone() {
        return new LinkedMultiValueMap(this);
    }

    public boolean equals(Object obj) {
        return this.targetMap.equals(obj);
    }

    public int hashCode() {
        return this.targetMap.hashCode();
    }

    public String toString() {
        return this.targetMap.toString();
    }
}

可以看到,它的本质上还是一个Map,只不过存放的value是List类型的而已。其中addAll 方法有多个重载,支持实现MultiValueMap接口类型的和参数为K,V类型的方法。而它的add函数运用了lamda表达式,当值为null的时候,会new一个LinkedList去填充,里面的默认属性为空。

LinkedMultiValueMap数据结构是 Map + Lis组合,其中 Map:LinkedHashMapList:LinkedList,所以 LinkedMultiValueMap具有以下特点,同时 具有 map(键值对)和list(有序)的特性。

总结:如果在遇到有单个key和多个value的情况下,可以采用LinkedMultiValueMap这种方法来实现我们的需求。

实例分享

代码语言:javascript
复制
MultiValueMap<String, String> stringMultiValueMap = new LinkedMultiValueMap<>();

stringMultiValueMap.add("早班 9:00-11:00", "周一");
stringMultiValueMap.add("早班 9:00-11:00", "周二");
stringMultiValueMap.add("中班 13:00-16:00", "周三");
stringMultiValueMap.add("早班 9:00-11:00", "周四");
stringMultiValueMap.add("测试1天2次 09:00 - 12:00", "周五");
stringMultiValueMap.add("测试1天2次 09:00 - 12:00", "周六");
stringMultiValueMap.add("中班 13:00-16:00", "周日");

//打印所有值
Set<String> keySet = stringMultiValueMap.keySet();
for (String key : keySet) {
    List<String> values = stringMultiValueMap.get(key);
    System.out.println(StringUtils.join(values.toArray(), " ") + ":" + key);

}

输出:
周一 周二 周四:早班 9:00-11:00
周三 周日:中班 13:00-16:00
周五 周六:测试1天2次 09:00 - 12:00

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • LinkedMultiValueMap源码
  • 实例分享
相关产品与服务
对象存储
对象存储(Cloud Object Storage,COS)是由腾讯云推出的无目录层次结构、无数据格式限制,可容纳海量数据且支持 HTTP/HTTPS 协议访问的分布式存储服务。腾讯云 COS 的存储桶空间无容量上限,无需分区管理,适用于 CDN 数据分发、数据万象处理或大数据计算与分析的数据湖等多种场景。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档