如何有效地迭代 Java Map 中的每个条目?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/46898/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 07:36:00  来源:igfitidea点击:

How do I efficiently iterate over each entry in a Java Map?

javadictionarycollectionsiteration

提问by iMack

If I have an object implementing the Mapinterface in Java and I wish to iterate over every pair contained within it, what is the most efficient way of going through the map?

如果我有一个Map在 Java 中实现接口的对象,并且我希望迭代其中包含的每一对,那么遍历映射的最有效方法是什么?

Will the ordering of elements depend on the specific map implementation that I have for the interface?

元素的顺序是否取决于我对界面的特定地图实现?

采纳答案by ScArcher2

Map<String, String> map = ...
for (Map.Entry<String, String> entry : map.entrySet()) {
    System.out.println(entry.getKey() + "/" + entry.getValue());
}

回答by pkaeding

Yes, the order depends on the specific Map implementation.

是的,顺序取决于具体的 Map 实现。

@ScArcher2 has the more elegant Java 1.5 syntax. In 1.4, I would do something like this:

@ScArcher2 具有更优雅的 Java 1.5 语法。在 1.4 中,我会做这样的事情:

Iterator entries = myMap.entrySet().iterator();
while (entries.hasNext()) {
  Entry thisEntry = (Entry) entries.next();
  Object key = thisEntry.getKey();
  Object value = thisEntry.getValue();
  // ...
}

回答by Leigh Caldwell

In theory, the most efficient way will depend on which implementation of Map. The official way to do this is to call map.entrySet(), which returns a set of Map.Entry, each of which contains a key and a value (entry.getKey()and entry.getValue()).

理论上,最有效的方式取决于 Map 的实现方式。官方的做法是调用map.entrySet(),它返回一组Map.Entry,每个都包含一个键和一个值(entry.getKey()entry.getValue())。

In an idiosyncratic implementation, it might make some difference whether you use map.keySet(), map.entrySet()or something else. But I can't think of a reason why anyone would write it like that. Most likely it makes no difference to performance what you do.

在一个特质实现,它可能使一些与你是否使用map.keySet()map.entrySet()或别的东西。但我想不出为什么有人会这样写。很可能它对您所做的性能没有影响。

And yes, the order will depend on the implementation - as well as (possibly) the order of insertion and other hard-to-control factors.

是的,顺序将取决于实现 - 以及(可能)插入顺序和其他难以控制的因素。

[edit] I wrote valueSet()originally but of course entrySet()is actually the answer.

[编辑] 我valueSet()最初写的,但当然entrySet()实际上是答案。

回答by Tom Hawtin - tackline

Typical code for iterating over a map is:

迭代地图的典型代码是:

Map<String,Thing> map = ...;
for (Map.Entry<String,Thing> entry : map.entrySet()) {
    String key = entry.getKey();
    Thing thing = entry.getValue();
    ...
}

HashMapis the canonical map implementation and doesn't make guarantees (or though it should not change order if no mutating operation are performed on it). SortedMapwill return entries based on the natural ordering of the keys, or a Comparator, if provided. LinkedHashMapwill either return entries in insertion-order or access-order depending upon how it has been constructed. EnumMapreturns entries in natural order of keys.

HashMap是规范的映射实现并且不做任何保证(或者如果没有对其执行变异操作,它不应该改变顺序)。SortedMap将根据键的自然顺序返回条目,或者 a Comparator,如果提供。LinkedHashMap将根据插入顺序或访问顺序返回条目,具体取决于它的构造方式。EnumMap以键的自然顺序返回条目。

(Update: I think this is no longer true.) Note, IdentityHashMapentrySetiterator currently has a peculiar implementation which returns the same Map.Entryinstance for every item in the entrySet! However, every time a new the iterator advances the Map.Entryis updated.

(更新:我认为这不再正确。)注意,IdentityHashMapentrySet迭代器目前有一个特殊的实现,它Map.EntryentrySet! 中的每个项目返回相同的实例。但是,每次新迭代器前进时Map.Entry都会更新。

回答by serg10

This is a two part question:

这是一个两部分的问题:

How to iterate over the entries of a Map- @ScArcher2 has answeredthat perfectly.

如何迭代 Map 的条目- @ScArcher2 已经完美地回答了这个问题。

What is the order of iteration- if you are just using Map, then strictly speaking, there are no ordering guarantees. So you shouldn't really rely on the ordering given by any implementation. However, the SortedMapinterface extends Mapand provides exactly what you are looking for - implementations will aways give a consistent sort order.

迭代的顺序是什么- 如果您只是使用Map,那么严格来说,没有顺序保证。所以你不应该真正依赖任何实现给出的顺序。但是,该SortedMap接口扩展Map并提供了您正在寻找的内容 - 实现将提供一致的排序顺序。

NavigableMapis another useful extension- this is a SortedMapwith additional methods for finding entries by their ordered position in the key set. So potentially this can remove the need for iterating in the first place - you might be able to find the specific entryyou are after using the higherEntry, lowerEntry, ceilingEntry, or floorEntrymethods. The descendingMapmethod even gives you an explicit method of reversing the traversal order.

NavigableMap是另一个有用的扩展- 这是一个SortedMap附加的方法,用于按条目在键集中的有序位置查找条目。所以可能这个可以去除需要摆在首位迭代-你也许可以找到具体的entry你是使用后higherEntrylowerEntryceilingEntry,或floorEntry方法。该descendingMap方法甚至为您提供了一种反转遍历顺序的显式方法。

回答by ckpwong

FYI, you can also use map.keySet()and map.values()if you're only interested in keys/values of the map and not the other.

仅供参考,您也可以使用map.keySet()map.values()如果你在地图的键/值只关心,而不是其他。

回答by Chris Dail

The correct way to do this is to use the accepted answer as it is the most efficient. I find the following code looks a bit cleaner.

正确的方法是使用公认的答案,因为它是最有效的。我发现以下代码看起来更简洁。

for (String key: map.keySet()) {
   System.out.println(key + "/" + map.get(key));
}

回答by serg

Example of using iterator and generics:

使用迭代器和泛型的例子:

Iterator<Map.Entry<String, String>> entries = myMap.entrySet().iterator();
while (entries.hasNext()) {
  Map.Entry<String, String> entry = entries.next();
  String key = entry.getKey();
  String value = entry.getValue();
  // ...
}

回答by abods

Try this with Java 1.4:

用 Java 1.4 试试这个:

for( Iterator entries = myMap.entrySet().iterator(); entries.hasNext();){

  Entry entry = (Entry) entries.next();

  System.out.println(entry.getKey() + "/" + entry.getValue());

  //...
}

回答by Fathah Rehman P

public class abcd{
    public static void main(String[] args)
    {
       Map<Integer, String> testMap = new HashMap<Integer, String>();
        testMap.put(10, "a");
        testMap.put(20, "b");
        testMap.put(30, "c");
        testMap.put(40, "d");
        for (Integer key:testMap.keySet()) {
            String value=testMap.get(key);
            System.out.println(value);
        }
    }
}

OR

或者

public class abcd {
    public static void main(String[] args)
    {
       Map<Integer, String> testMap = new HashMap<Integer, String>();
        testMap.put(10, "a");
        testMap.put(20, "b");
        testMap.put(30, "c");
        testMap.put(40, "d");
        for (Entry<Integer, String> entry : testMap.entrySet()) {
            Integer key=entry.getKey();
            String value=entry.getValue();
        }
    }
}