Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Iterate to find a Map entry at an index?

Tags:

java

I have a LinkedHashMap. I want to get the Foo at index N. Is there a better way of doing this besides iterating until I find it?:

int target = N;
int index = 0;
for (Map.Entry<String, Foo> it : foos.entrySet()) {
    if (index == target) {
        return it.getValue();
    }
    index++;
}

I have to do get random elements from the map by an index about 50 times for some operation. The map will have about 20 items in it.

Thanks

like image 742
user291701 Avatar asked Oct 09 '10 02:10

user291701


2 Answers

List<Entry<String,Foo>> randAccess = new ArrayList<Entry<String,Foo>>(foos.entrySet());

Then for index N with O(1) access...

randAccess.get(N)
like image 51
Mark Elliot Avatar answered Nov 01 '22 08:11

Mark Elliot


@Mark's solution is spot on. I'd just like to point out that the offsets (positions) of the entries in a map (of any kind) are not stable. Each time an entry is added or removed, the offsets of the remaining entries may change. For a HashMap or LinkedHashMap, you've no way of knowing which entry's offsets will change.

  • For a regular HashMap, a single insertion can apparently "randomize" the entry offsets.
  • For a LinkedHashMap, the order of the entries is stable, the actual entry offsets are not.

The instability of the offsets and the fact that finding entry at a given offset is expensive for all standard map implementations are the reasons why the Map interface does not provide a get(int offset) method. It should also be a hint that it is not a good idea for an algorithm to need to do this sort of thing.

like image 24
Stephen C Avatar answered Nov 01 '22 08:11

Stephen C