从嵌套的hashmap中删除条目时java中的ConcurrentModificationException

时间:2018-05-04 13:26:37

标签: java exception-handling java-8 java-stream concurrenthashmap

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.IntStream;


public class HelloWorld{

     public static void main(String[] args) {
        Map<String, String> map = new HashMap<>();

        IntStream.range(0, 20).forEach(i -> map.put(Integer.toString(i), i % 2 == 0 ? null : "ok"));

        for (Map.Entry<String, String> entry : map.entrySet()) {
            if (entry.getValue() == null) {
                map.remove(entry.getKey());
            }
        }
    }
}

这是一个示例代码,我试图从给定的Hashmap中删除空值。但是这段代码给出了ConcurrentModificationException。知道如何解决这个问题吗?

编辑:感谢YCF_L,如果我用map.entrySet().removeIf(entity -> entity.getValue() == null);

替换整个循环,上面的代码会有所帮助

问题2:

如果散列图是嵌套的,该怎么办?

  • 案例1 - &gt;如果value为null,我想删除
  • 案例2 - &gt;我想删除,如果值是一个hashmap,其嵌套哈希中的每个元素都为null,如果嵌套的嵌套嵌套,则依此类推。

例如:

public static void removeEmptyValues(Map<String, Object> entityMap) {
    for (Map.Entry<String, Object> entry : entityMap.entrySet()) {
        String key = entry.getKey();
        Object value = entry.getValue();
        if (value == null) {
            entityMap.remove(key);
        } else if (value instanceof Map) {
            removeEmptyValues((Map) value);
            if (((Map) value).isEmpty()) {
                entityMap.remove(key);
            }
        }
    }
}

1 个答案:

答案 0 :(得分:2)

您可以使用Collection::removeIf这样解决此问题:

map.entrySet().removeIf(entity -> entity.getValue() == null);

抛出此错误的原因是您同时迭代Hashmap的值,通过删除值来更改它,然后继续迭代。这就是引发异常的原因。

另见答案:

Iterating through a Collection, avoiding ConcurrentModificationException when removing in loop