Remove a key in hashmap when the value's hashs

2019-04-28 17:31发布

问题:

I have a hashmap that maps strings keys to hashsets values, and I want to remove a key from the hashmap when the hashmaps's hashset value is empty. I'm having trouble approaching this. Here's what I've tried but I'm very stuck:

for(Map.Entry<String, HashSet<Integer>> entr : stringIDMap.entrySet()) 
{  

                String key = entr.getKey();  

                if (stringIDMap.get(key).isEmpty())
                {

                    stringIDMap.remove(key);
                    continue;
                }
     //few print statements...
}

回答1:

In order to avoid ConcurrentModificationException, you need to use the Iterator interface directly:

Iterator<Map.Entry<String, HashSet<Integer>>> it = stringIDMap.entrySet().iterator();
while (it.hasNext()) {
    Map.Entry<String, HashSet<Integer>> e = it.next();
    String key = e.getKey();
    HashSet<Integer> value = e.getValue();
    if (value.isEmpty()) {
        it.remove();
    }
}

The reason your current code doesn't work is that you are attempting to remove elements from the map while iterating over it. When you call stringIDMap.remove(), this invalidates the iterator that the for-each loop uses under the cover, making further iteration impossible.

it.remove() solves this problem as it does not invalidate the iterator.



回答2:

 Iterator<String> iterator = mMapFiles.keySet().iterator();
    while (iterator.hasNext()){
        if ( mMapFiles.get( iterator.next() ).size() < 1 )
            iterator.remove();
    }


回答3:

Since Java 8, there is an excelent short solution with lambda:

stringIDMap.entrySet().removeIf(ent -> ent.getValue().isEmpty());

or you can use more concise way by passing method reference

stringIDMap.values().removeIf(Set::isEmpty);