gpt4 book ai didi

java - 如果我只需要保证 `happens-before` 关系,而不是原子性,我应该使用并发类还是同步块(synchronized block)?

转载 作者:行者123 更新时间:2023-12-01 18:42:32 25 4
gpt4 key购买 nike

我正在开发一个池机制。池中的对象将被不同的线程使用。因此,我需要保证在访问这些对象的非最终属性时存在 happens-before 关系。

由于给定的对象一次只能由一个线程访问,因此我不需要保证任何原子性。当只需要实现 happens-before 时,什么更优化?每次读取或修改非最终属性之一时,要在最终属性上使用同步块(synchronized block)吗?或者使用并发类,例如 ConcurrentMap?

(我问这个问题不是为了池本身的属性,这显然需要提供原子性;我只是问从池中获取的对象的属性)

最佳答案

To use a synchronized block on a final attribute each time I read or modify one of the non-final attribute? Or to use concurrent classes, such as a ConcurrentMap?

同步是围绕称为内在锁或监视器锁的内部实体构建的。每个对象都有一个与其关联的内在锁。按照惯例,需要对对象字段进行独占和一致访问的线程必须在访问对象字段之前获取该对象的内在锁,然后在访问完这些字段后释放该内在锁。

ConcurrentMap 的实现,即 ConcurrentHashMap 使用可重入锁 是互斥锁,Lock 由 lock() 方法获取,并由 Thread 持有,直到调用 unlock() 方法。虽然,ReentrantLock 提供与隐式锁相同的可见性和顺序保证,由 synchronized 关键字 获取,但它提供了更多功能,并且在某些方面有所不同:

  1. ReentrantLock 可以通过指定公平属性 来实现公平,以便在发生争用时为最长等待线程提供锁定。
  2. 提供方便的tryLock()方法来获取锁,仅当锁可用或未被任何其他线程持有时,减少等待锁的线程阻塞。 tryLock() 带超时功能,可用于在某个时间段内锁不可用时超时。
  3. 如果使用synchronized关键字,线程可能会无限期地被阻塞等待锁定,并且无法控制这一点。 ReentrantLock提供了一个名为lockInterruptically()的方法,可以用来在线程等待锁时中断线程。

使用可重入锁的示例可以从ConcurrentHashMap的内部replace(K key, V oldValue, V newValue)函数中看到实现:

boolean replace(K key, int hash, V oldValue, V newValue) { 
// called by replace(K key, V oldValue, V newValue)
lock(); // acquire the lock
try {
HashEntry<K,V> e = getFirst(hash);
while (e != null && (e.hash != hash || !key.equals(e.key)))
e = e.next;

boolean replaced = false;
if (e != null && oldValue.equals(e.value)) {
replaced = true;
e.value = newValue;
}
return replaced;
} finally {
unlock(); // unlock
}
}

还有其他函数,如put()writeObject(java.io.ObjectOutputStream)等,也是使用可重入同步实现的/em>使用ReentrantLock,如果没有它,同步代码将必须采取许多额外的预防措施,以避免线程导致自身阻塞。这就是为什么我认为对于你的情况 ConcurentMap 更可取。

引用:

  1. Intrinsic Locks and Synchronization
  2. ReentrantLock Class
  3. Difference between synchronized vs ReentrantLock
  4. ConcurrentHashMap

关于java - 如果我只需要保证 `happens-before` 关系,而不是原子性,我应该使用并发类还是同步块(synchronized block)?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19340353/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com