java方法同步和读/写互斥

我在类中有两个方法read()write() ,如下所示。

 class Store { public void write() { // write to store; } public string read() { // read from store; } } 

1) Store对象是单例。

2)我有一个Writer类,它将写入商店和几个同时从商店读取的Reader类。

我的要求是,当作家写信给商店时,所有的读者都应该等待。 即,当控制在write() ,应该阻止对read()所有调用。 我该如何实现这一目标? 我已经尝试在write()方法中synchronize(Store.class) ,但似乎不适合我。

在这种情况下,最好的选择是使用读写器锁: ReadWriteLock 。 它允许单个编写器,但允许多个并发读取器,因此它是此类场景的最有效机制。

一些示例代码:

 class Store { private ReadWriteLock rwlock = new ReentrantReadWriteLock(); public void write() { rwlock.writeLock().lock(); try { write to store; } finally { rwlock.writeLock().unlock(); } } public String read() { rwlock.readLock().lock(); try { read from store; } finally { rwlock.readLock().unlock(); } } } 

synchronized是最简单的解决方案,所以你应该解释你的意思“看起来对我不起作用”并且可能告诉我们你是如何使用它的。

更好的解决方案是使用ReentrantReadWriteLock,因为它也允许并发访问读者。

当某个方法在某个对象上同步时,执行此方法的线程会阻止尝试输入在同一对象上同步的另一个块/方法的所有其他线程。

因此,如果您希望编写器线程禁止任何读取器线程读取,则必须同步write和read方法。 没有理由在Store类上进行同步。 在Store对象上进行同步更自然:

 public synchronized void write() { write to store; } public synchronized String read() { read from store; } 

然而,这可能有一个缺点:它还禁止两个读取器线程同时读取。 如果您真的需要这样做,您应该使用ReadWriteLock 。 但这会导致代码性能降低,难以理解和维护。 如果我已经测量到需要它,我只会使用它。

使用java.util.concurrent包中的ReadWriteLock

请仔细阅读本文:

https://blog.takipi.com/java-8-stampedlocks-vs-readwritelocks-and-synchronized/

  • RWLocks可能很慢,特别是当有很多读者可以写作时
  • synchronized是平均最快可靠的
  • 有像StampedLock这样的新锁