反向迭代 LinkedHashMap

Iterate over LinkedHashMap in reverse

我有一个LinkedHashMap(因为输入的顺序很重要)。 我希望能够像数组一样迭代它的条目(键,值对) 从 end 到 start 所以 foreach methods 不适合这里 类似于:

for (int i = DestIndexStartPair.entrySet().size() , i> 0 ; i--) {
    entry = DestIndexStartPair.entrySet()[i];
    String Endsection = output.substring(entry.value());
    System.out.println(Endsection );
}

EntrySet 是一个集合,因此通常没有索引。

所以,你需要的是...

for(Entry<K,V> entry : DestIndexStartPair.entrySet()) {
    String Endsection = output.substring(entry.value()); // whatever output is
    System.out.println(Endsection );
}

...然后存储结果,并取反

工作解决方案

List<Entry<Foo,Bar>> list = new ArrayList<Entry<Foo,Bar>>(map.entries());

for (int i = list.size() - 1; i >= 0; i--) {
    Entry<Foo,Bar> entry = list.get(i);
}

显然,这里的权衡是您必须将整个地图复制到数组列表中。如果您的地图太大(任何太大),您可能会遇到性能和内存问题。

没有有效的方法以相反的顺序迭代 Set(例如 entrySet)。如果您需要双向迭代,那么对于相反的方向,最好的方法是复制到一个临时列表中,然后反向迭代该列表。

当然,如果你只需要一个方向,那么你应该确保 LinkedHashMap那个 顺序而不是相反。

查看地图实施可能会有更多帮助。可能通过以更合适的方式覆盖,这可以在性能或线程安全等方面以平衡的方式实现。但这里有一些小技巧可能会有所帮助,

public class HackedLinkedHashMap<K,V> extends LinkedHashMap<K,V> implements Map<K,V> {

private LinkedList<K> keyList = new LinkedList<>();

@Override
public V put(K key, V value){
    V obj = super.put(key, value);
    keyList.addFirst(key);

    return obj;
}

public LinkedList<K> getReversedKeyList(){
    return keyList;
}}


public static void main(String[] args) {
    System.out.println("Test conference");
    HackedLinkedHashMap<Integer, Integer> map = new HackedLinkedHashMap();
    for(Integer i=0;i<100;i++){
        map.put(i, i);
    }   
    Iterator<Integer> iterator = map.getReversedKeyList().iterator();
    while (iterator.hasNext()){
        System.out.println(iterator.next());
    }
}