我们可以使用entrySet()方法来迭代存储在Node[]表字段中的hashmap键值对。
HahMap<K,V> hashmap = new HashMap<>() ;
public Set<Map.Entry<K,V>> entrySet()
{
Set<Map.Entry<K,V>> es;
return (es = entrySet) == null ? (entrySet = new EntrySet()) : es;
}
当我们在 for-each 循环中使用它时,例如:
for ( Map.Entry<K,V> entry : hashmap.entrySet () )
{
...
// entry is an object of return type Map.Entry and object type Node .
// got the object type by calling entry.getClass() and also no other inner class other than Node implements Map.Entry . ;
}
这些对象存储在 Set 中。但是将它们链接到具有键值对的字段表的代码在哪里。
例如: 在 toString() 方法中,当我们使用 iterator() 方法获取 Iterable 并调用 Iterable 上的 next() 方法时,调用将转到 HashIterator 类的 nextNode() ,其中返回的对象链接到 HashMap 类的表字段。 但这里会发生什么?请帮忙 。
最佳答案
您似乎缺乏对 View 是什么的理解。 View 没有存储数据,只是通过委托(delegate)给实际数据对象来实现某个接口(interface)。
一个简单的例子是通过 Collections.unmodifyingList(…)
创建的列表 View ,它不包含任何数据,但将所有方法调用委托(delegate)给原始列表,不包括当然是修改方法。
条目集通过委托(delegate)给底层映射来实现Set
接口(interface)。最值得注意的是,通过返回一个迭代器,因为大多数方法都是在此基础上构建的,所以只有少数其他方法会为了性能而被重写,例如size()
直接委托(delegate)给 map 的 size()
。因此,如果条目集看起来好像包含某些内容,那么它确实包含某些内容,因为迭代器在遍历期间报告了它。
Hashmap 的条目集迭代器迭代内部条目数组,就像键集迭代器和值集合迭代器一样。它们之间的唯一区别在于它们在 next()
方法中返回哪个对象,条目集迭代器仅返回条目,其他两个分别提取键。条目的值。这就是为什么这些迭代器只重写单个方法。
请注意,这种交互也可以反过来看。当您通过扩展 AbstractMap
实现 Map
时,entrySet()
是您需要实现的唯一方法,所有其他映射方法都已通过对条目集的委托(delegate)来实现。不过,您可能会为了性能而覆盖其中一些。但实际上包含数据的问题是没有意义的,Map
和条目 Set
都是相同底层数据的 View 。
也许下面的例子有帮助:
String[][] pairs={ {"foo","bar"}, {"hello","world"} };
Map<String,String> map = new AbstractMap<String, String>() {
public Set<Map.Entry<String, String>> entrySet() {
return new AbstractSet<Entry<String, String>>() {
public Iterator<Map.Entry<String, String>> iterator() {
return Arrays.stream(pairs)
.<Entry<String,String>>map(p -> new SimpleImmutableEntry<>(p[0],p[1]))
.iterator();
}
public int size() {
return pairs.length;
}
};
}
};
System.out.println(map.get("foo"));
System.out.println(map.containsKey("hello"));
System.out.println(map.containsValue("world"));
map.forEach((k,v) -> System.out.println(k+" -> "+v));
System.out.println(map);
它创建了一个永远不会被放入的不可变映射。尽管如此,它还是通过所有 Map
方法报告了预期的内容,只是因为条目集迭代器报告了此内容。
关于java - 无法理解entrySet()方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45368913/