为什么LinkedHashMap keyset()没有返回LinkedHashSet vs Set?

Bra*_*ing 2 java collections linkedhashmap linkedhashset

我已经阅读了java文档以及这篇文章中的LinkedHashMaps keyset()维护订单. 是否保证从LinkedHashMap对象返回键和值的顺序?

我的问题是,如果它保证顺序那么为什么不LinkedHashMap返回一个类型的对象Set保证顺序的源代码LinkedHashSet

我可以想到的一个原因是LinkedHashSet使用了一个可以增加内存分配的映射(取决于AbstractSet的实现方式).是不是因为它的未来证明了keyset的实现?

就像这个帖子在这篇文章中所说:使用List或Collection更好吗?

返回列表符合最高适当接口的编程.

返回集合会导致用户不明确,因为返回的集合可能是:Set,List或Queue.

那么,没有阅读文档的keyset()不是这个含糊不清的?

keyset() 源代码:

public Set<K> keySet() {
    Set<K> ks = keySet;
    return (ks != null ? ks : (keySet = new KeySet()));
}

private final class KeySet extends AbstractSet<K> {
    public Iterator<K> iterator() {
        return newKeyIterator();
    }
    public int size() {
        return size;
    }
    public boolean contains(Object o) {
        return containsKey(o);
    }
    public boolean remove(Object o) {
        return HashMap.this.removeEntryForKey(o) != null;
    }
    public void clear() {
        HashMap.this.clear();
    }
}
Run Code Online (Sandbox Code Playgroud)

Aus*_*n D 5

它返回一个Set由接口定义的Map。ASet是不包含重复元素的简单集合。另一方面,aList是有序集合(也称为序列)。这List接口未指定元素是唯一的。

尽管如此,该LinkedHashMap实现实际上返回了底层的 keySet,它是 a LinkedKeySet,并且该forEach()方法LinkedKeySet是保序的,即:

//from the source code for the LinkedHashMap:
public Set<K> keySet() {
    Set<K> ks;
    return (ks = keySet) == null ? (keySet = new LinkedKeySet()) : ks;
}
Run Code Online (Sandbox Code Playgroud)

因此,在这种情况下,元素既是唯一的又是有序的。


And*_*eas 5

"为什么LinkedHashMap返回的源代码没有保证顺序Object的类型?"SetLinkedHashSet

因为它LinkedHashSet是一个具体的类,它自己的实现维护自己的数据,并且该keyset()方法必须返回一个视图Map,所以它不能只是将关键数据复制到一个LinkedHashSet.见javadoc:

返回Set此映射中包含的键的视图.该集由地图支持,因此对地图的更改将反映在集中,反之亦然.