【问题标题】:is reentrant lock is complete replacement for synchronisation?可重入锁是同步的完全替代品吗?
【发布时间】:2016-10-10 14:50:00
【问题描述】:

我浏览了文章“http://www.ibm.com/developerworks/java/library/j-jtp10264/”。他们提到“Lock 框架是同步的兼容替代品”。我知道通过使用可重入锁,我们可以跨方法持有锁,等待锁一段时间(使用同步块(或)方法是不可能的)。我的疑问是,是否可以用可重入锁的同步机制替换应用程序?

例如,我想实现一个线程安全的栈数据结构,所有的push、pop、getTop方法都是同步的,所以在多线程环境下,一次只能有一个线程可以访问一个同步方法(如果一个线程正在使用 push 方法,没有其他线程可以访问 push、pop、getTop(或)任何其他 Stack 类的同步方法)。是否可以使用可重入锁实现相同的线程安全堆栈数据结构?如果可能,请提供一个例子来理解这一点。

【问题讨论】:

  • 自 Java 5 以来,synchronized 语句有许多替代方案,而不仅仅是Locks。在您的情况下,您可能希望利用 java.util.concurrent 包中的同步集合,而不是重新发明轮子。
  • 是的。我知道并发收集,但我的问题是,是否可以使用锁框架实现完整的线程安全数据结构。
  • 你不能用Locks 但你可以用synchronized 做的一件事是通过池对象滥用它。总的来说可能不是一件坏事。

标签: java multithreading synchronization locking


【解决方案1】:

你可以用synchronized 做任何事情,你也可以用ReentrantLock 做任何事情,但反之则不行。话虽如此,如果您只需要 lock/unlock 语义,我建议您使用 synchronized,因为在我看来,它更具可读性。

【讨论】:

    【解决方案2】:

    答案是“是”。

    lock - 使用unlock 对而不是synchronize( ) { ... }Condition 中的 awaitsignalwaitnotify 的替代品。

    【讨论】:

      【解决方案3】:

      Brian Goetz 在第 13.4 章的"Java Concurrency in Practice" 中讨论了这个问题:

      ReentrantLock 是一种高级工具,适用于内在锁定不实用的情况。如果您需要它的高级功能,请使用它:定时、轮询或可中断的锁定获取、公平队列或非块结构锁定。否则,首选同步。

      我完全同意,因为恕我直言:

      synchronized (lock) {
          // ...
      }
      

      比这更易读,更不容易出错:

      try {
          lock.lock();
          // ...
      } finally {
          lock.unlock();
      }
      

      长话短说:从技术角度来看,是的,您可以将 synchronized 替换为 ReentrantLock,但我不会这样做。

      同时检查以下问题:

      【讨论】:

        【解决方案4】:

        ReentrantLock 是同步的替代方案之一。

        具有与使用同步方法和语句访问的隐式监视器锁相同的基本行为和语义的可重入互斥锁,但具有扩展功能。

        有关同步的其他替代方法(Concurrent Collections、Atomic variables、Executors、ThreadLocal variables),请参阅此问题

        Avoid synchronized(this) in Java?

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2014-09-22
          • 2011-03-17
          • 2019-09-18
          • 2011-03-30
          • 2017-04-13
          相关资源
          最近更新 更多