Lock与synchronized对比

Love The Way You Lie 2021-09-27 14:26 467阅读 0赞

































Lock接口方法 功能
lock.lock 获取锁 阻塞
lock.tryLock 获取锁 成功返回true 失败false
lock.tryLock(1, TimeUnit.SECONDS) 等待制定时间 获取锁 成功返回true 失败false
lock.lockInterruptibly 注意,如果需要正确中断等待锁的线程,必须将获取锁放在外面,然后将InterruptedException抛出 调用Thread.interrupt方法打断
lock.unlock 释放锁
设置公平锁 Lock lock = new ReentrantLock(true);//true为公平锁

synchronized 与 Lock接口功能区别














































类别 synchronized Lock
存在层次 Java的关键字,在jvm层面上 是一个类
锁的释放 1、以获取锁的线程执行完同步代码,释放锁 2、线程执行发生异常,jvm会让线程释放锁 在finally中必须释放锁,不然容易造成线程死锁
锁的获取 假设A线程获得锁,B线程等待。如果A线程阻塞,B线程会一直等待 分情况而定,Lock有多个锁获取的方式,具体下面会说道,大致就是可以尝试获得锁,线程可以不用一直等待
锁状态 无法判断 可以判断
锁类型 可重入 不可中断 非公平 可重入 可判断 可公平(两者皆可)
性能 用CAS来实现 用CAS来实现
功能 synchronized的使用简单点 Lock提供的功能丰富点

Demo简单示例

  1. import java.util.concurrent.ExecutorService;
  2. import java.util.concurrent.Executors;
  3. import java.util.concurrent.locks.Lock;
  4. import java.util.concurrent.locks.ReentrantLock;
  5. /**
  6. *
  7. * @author gyn 实现一个线程安全的计数器
  8. */
  9. public class Test100 implements Runnable {
  10. public final static ExecutorService EXECUTOR = Executors.newFixedThreadPool(100);
  11. public static volatile int li = 0;
  12. public static volatile int si = 0;
  13. public final static Lock lock = new ReentrantLock(true);//公平锁
  14. /**
  15. * Lock实现
  16. */
  17. public static void getLockInt() {
  18. lock.lock();// 获取锁
  19. try {
  20. li++;
  21. } catch (Exception e) {
  22. // TODO: handle exception
  23. } finally {
  24. lock.unlock();// 释放锁
  25. }
  26. }
  27. /**
  28. * synchronized关键字实现
  29. */
  30. public static synchronized void getSynInt() {
  31. si++;
  32. }
  33. @Override
  34. public void run() {
  35. // TODO Auto-generated method stub
  36. for (int i = 0; i < 100; i++) {
  37. getSynInt();
  38. }
  39. for (int i = 0; i < 100; i++) {
  40. getLockInt();
  41. }
  42. }
  43. public static void main(String[] args) throws InterruptedException {
  44. for (int i = 0; i < 100; i++) {
  45. EXECUTOR.execute(new Test100());
  46. }
  47. EXECUTOR.shutdown();
  48. for (;;) {
  49. // 判断线程池任务是否执行完毕
  50. if (EXECUTOR.isTerminated()) {
  51. System.out.println("Lock实现 li=" + Test100.li);
  52. System.out.println("synchronized关键字实现 si=" + Test100.si);
  53. break;
  54. } else {
  55. System.out.println("线程未结束");
  56. Thread.sleep(200);
  57. }
  58. }
  59. }
  60. }

控制台输出————————-都是线程安全的

  1. 线程未结束
  2. Lock实现 li=10000
  3. synchronized关键字实现 si=10000

发表评论

表情:
评论列表 (有 0 条评论,467人围观)

还没有评论,来说两句吧...

相关阅读

    相关 synchronizedlock

    1、两个线程同时访问一个对象的相同的synchronized方法 同一实例拥有同一把锁,其他线程必然等待,顺序执行 不同的实例拥有的锁是不同的,所以不影响,并行执行

    相关 Locksynchronized 的区别

    多次思考过这个问题,都没有形成理论,今天有时间了,我把他总结出来,希望对大家有所帮助     1、ReentrantLock 拥有Synchronized相同的并发性和内