我有以下类,其声明为私有(private)线程安全集合:
final private ConcurrentHashMap<Book,BookLog> booklogMap;
根据这个page ,因为日期是可变的并且它在不可变的类中使用,所以必须创建一个防御性副本以避免在创建后更改对象。他们在构造函数中创建一个防御性副本,如下所示:
fDateOfDiscovery = new Date(aDateOfDiscovery.getTime())
在 setter/getter 中像这样:
public Date getDateOfDiscovery() {
return new Date(fDateOfDiscovery.getTime());
}
那么我如何在构造函数中正确创建 ConcurrentHashMap 的防御性副本?我无法使用Collections.modifyingMap()
,因为它会遇到强制转换问题。
最佳答案
您可能想也可能不想使用Collections.unmodifyingMap()
,因为它返回一个Map
,而不是ConcurrentHashMap
,而且您可能无法转换它(虽然我还没有尝试过)。这可能并不是一件坏事,因为其他类可能不需要知道这个特定的 Map
属于并发哈希类型。
@resueman 在评论中建议您可以使用
new ConcurrentHashMap<Book, Booklog>(booklogMap);
这会创建 ConcurrentHashMap 本身的(防御性)副本,但不会创建 Map 内容的副本。这可能没问题,也可能没问题,具体取决于 Map
用户想要用它做什么。
并且,如果您决定需要复制内容,则必须决定是否复制这些副本包含的字段值。依此类推,直到停止。
关于java - 如何制作线程安全集合的防御性副本,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35350075/