我正在尝试了解synchronizedCollection
,synchronizedList
,synchronizedMap
,synchronizedSet
和其他此类方法会做什么。据我了解,可以在块和方法上进行同步,而不是在课堂上完成,因此,如果我有一个哈希图,请说。
HashMap<Integer,String> hashMap = new HashMap<Integer,String>();
HashMap<Integer,String> syncHashMap = Collections.synchronizedMap(hashMap);
问题
上述代码也只是同步整个
syncHashMap
类或其中的每种方法?如果我们可以简单地使用threadSafe集合,例如
ConcurrentHashMap
或SynchronizedMap
在多线程方案中Collections.synchronizedMap(hashMap)
和其他类似方法collections class
将深深欣赏到这一点上的某个方向,谢谢。
不确定同步整个Synchashmap类和中的每种方法是什么意思。
如果您查看方法Collections.synchronizedMap(hashMap)
的源代码,则会发现它使用synchronized
关键字来装饰原始映射的所有方法。这意味着对于装饰的地图对象,您只能一次调用其一种方法之一。但是不同的地图,您可以一次致电。
- 您可以在这里找到它们的用法。consurrenthashmap vs同步hashmap
据我所知, Collections.synchronizedMap
不能保证存储对象中的字段值会同步,但每个 entry 在synchronized
方法中修改时,将对地图进行同步。它不能保证其他任何东西。每当在另一个线程中修改同步映射时,其他线程中的其他参考文献都会同步。
这是我根据此来源和Java文档对此的表面理解。
有几个访问您的主题的术语。
同步
有许多接口和类,可以帮助您在线程之间同步您的代码。信号量,循环架或同步集合(例如阻止式(。有关这些类的列表,请参见Java.util.concurrent软件包。
synchronized
块也是一种同步的方式,尽管使用它正确需要更多的经验。
互惠x
不同的语言(和库(以不同的方式实现标准互斥。这个想法保持不变 - 为了继续执行特定代码,必须获得互斥的代币,必须获得互斥品。在Java中,此收购发生在输入synchronized
块之前。
线程安全
简单地说,当可以同时从任意数量的线程以任何顺序访问其所有方法时,类都是线程安全的。有几种方法可以实现螺纹安全。例如,字符串是线程安全的。它们没有同步,但它们是不变的,也会导致线程安全。所有Collections.synchronized*()
方法返回线程安全包装器的收集器包装器,私密地说,所有未来*(*请参见发生 - 与之相关联(通过这些包装器执行对它们的访问(这就是为什么初学者仅在new
对象上调用Collections.synchronized*()
的好规则。<<<<<<<<<<<<<<
答案
拥有以前段落的知识,以回答您的问题:不,它不会同步类。它根本不会更改原始的Collection
实现。它确实创建了一个读写线程安全的螺纹同步的可变类产品,但是。
在回答您的问题之前,让我们重申同步的一些基础
- 同步始终在对象/实例上。每个同步实例都由锁(称为Mutex(守护。
- 任何在对象上调用同步方法的线程,都必须先获取该锁定,然后调用该方法。
- 不需要此锁定的锁定,为什么要调用非精神化方法。
回答您的问题:
- 因此,上述代码是否仅同步整个同步类或其中的每个方法?
是的。只需在此处查看Collections的源代码。SynchronizedMap。请注意,几乎每种方法都具有同步(MUTEX(块。
- 如果我们可以简单地使用多线程方案中的conturrenthashmap或同步图等线程安全集合,那么collections.synchronizedmap(hashmap(和集合类中的其他类似方法是什么?
嗯,同步每种方法的缺点(包括只读类型的方法(。它不必要地减慢了读取操作,因此您的观察结果是正确的,即使用诸如ConsturrentHashMap之类的实现,该实现仅锁定正在修改集合的方法。仅读取方法不会同步,因此在多线程方案中使用并发读/写操作更快。
唯一的优势收集。SynchronizedMap优惠是保留输入的键的顺序。因此,当您需要使用collections.synchronizedmap时。