【发布时间】:2018-05-04 08:28:25
【问题描述】:
在我的项目中,我构建了 Jersey Web 服务。该服务有计划任务,每分钟运行一次并填充(通过 putIfAbsent 函数)并发哈希映射(但之前清除它)。此外,Web 服务具有返回地图 json 的端点:
return gson.toJson(map, type)
通过 JAVA API 函数 clear 不是并发函数,gson.toJson 只使用 Map API 函数,所以我需要并发 clear 和 getMap/copyMap 函数。所以我想通过并发函数使用自己实现这些功能:
public class ExtendedConcurrentHashMap<K,V> extends ConcurrentHashMap<K,V> {
private final ConcurrentHashMap<K,V> map;
public ExtendedConcurrentHashMap(ConcurrentHashMap<K,V> map) {
this.map = map;
}
public void clear() {
ConcurrentHashMap.KeySetView<K,V> keySet = map.keySet(); //concurrent function
Iterator<K> iterator = keySet.iterator();
while(iterator.hasNext()) {
K keyToRemove = iterator.next();
map.compute(keyToRemove, (key,value) -> null); // concurrent function
}
}
public Map<K,V> getMap() {
Map<K,V> mapCopy = new HashMap<>();
map.forEach((key,value) -> mapCopy.put(key,value)); // concurrent function
return mapCopy;
}
}
这是正确的方法吗?我不想使用读/写锁或同步函数,因为从端点性能获取 json 对于我的 Web 服务非常重要。
部分填充的地图不会打扰我。在读/写/更新期间获得性能而不是获得异常对我来说最重要
【问题讨论】:
-
clear() 如果你使用 concurenthashmap 是线程安全的
-
只需使用
Collections.synchronizedMap包装一个普通的HashMap。这将为您提供一致的数据视图。 -
@teppic 并在多线程环境中杀死性能:)
-
@Cargeh:我保证 op 不会注意到差异。
-
为什么不使用 volatile 字段交换为不可变映射?这样你就不会看到部分人口稠密的地图了
标签: java concurrency gson concurrenthashmap