synchronized和java.util.concurrent.locks.Lock的异同【转】

本文详细对比了Java中的synchronized和ReentrantLock的区别,包括线程语义、性能表现和使用场景。重点介绍了ReentrantLock的优势及何时应该使用它,通过代码示例展示了如何在不同情况下灵活运用这两种锁机制。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

主要相同点:Lock能完成synchronized所实现的所有功能
主要不同点:Lock有比synchronized更精确的线程语义和更好的性能,当许多线程都在争用同一个锁时,使用 ReentrantLock 的总体开支通常要比 synchronized 少得多。 synchronized会自动释放锁,而Lock一定要求程序员手工释放,并且必须在finally从句中释放。

 

ReentrantLock 保护代码块

 

我们什么时候才应该使用 ReentrantLock 呢?答案非常简单 —— 在确实需要一些 synchronized 所没有的特性的时候,比如时间锁等候、可中断锁等候、无块结构锁、多个条件变量或者锁投票。 ReentrantLock 还具有可伸缩性的好处,应当在高度争用的情况下使用它,但是请记住,大多数 synchronized 块几乎从来没有出现过争用,所以可以把高度争用放在一边。我建议用 synchronized 开发,直到确实证明 synchronized 不合适,而不要仅仅是假设如果使用 ReentrantLock “性能会更好”。请记住,这些是供高级用户使用的高级工具。(而且,真正的高级用户喜欢选择能够找到的最简单工具,直到他们认为简单的工具不适用为 止。)。一如既往,首先要把事情做好,然后再考虑是不是有必要做得更快

 

Resource4.java
package com.zj.lock;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
public class Resource4 {
  private Lock lock1 = new ReentrantLock();
  private Lock lock2 = new ReentrantLock();
  private Lock lock3 = new ReentrantLock();
  public void f() {
    // other operations should not be locked...
    System.out.println(Thread.currentThread().getName()
       + ":not synchronized in f()");
    lock1.lock();
    try {
      for (int i = 0; i < 5; i++) {
       System.out.println(Thread.currentThread().getName()
           + ":synchronized in f()");
       try {
         TimeUnit.SECONDS.sleep(3);
       } catch (InterruptedException e) {
         e.printStackTrace();
       }
      }
    } finally {
      lock1.unlock();
    }
  }
  public void g() {
    // other operations should not be locked...
    System.out.println(Thread.currentThread().getName()
       + ":not synchronized in g()");
    lock2.lock();
    try {
      for (int i = 0; i < 5; i++) {
       System.out.println(Thread.currentThread().getName()
           + ":synchronized in g()");
       try {
         TimeUnit.SECONDS.sleep(3);
       } catch (InterruptedException e) {
         e.printStackTrace();
       }
      }
    } finally {
      lock2.unlock();
    }
  }
  public void h() {
    // other operations should not be locked...
    System.out.println(Thread.currentThread().getName()
       + ":not synchronized in h()");
    lock3.lock();
    try {
      for (int i = 0; i < 5; i++) {
       System.out.println(Thread.currentThread().getName()
           + ":synchronized in h()");
       try {
         TimeUnit.SECONDS.sleep(3);
       } catch (InterruptedException e) {
         e.printStackTrace();
       }
      }
    } finally {
      lock3.unlock();
    }
  }
  public static void main(String[] args) {
    final Resource4 rs = new Resource4();
    new Thread() {
      public void run() {
       rs.f();
      }
    }.start();
    new Thread() {
      public void run() {
       rs.g();
      }
    }.start();
    rs.h();
  }
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值