zoukankan      html  css  js  c++  java
  • Java之线程同步的三种方法

    第一种:同步代码块

    同步代码块的核心是设置同步监视器,原则上在Java中可以设置任何对象为同步监视器,但通常设置可能并发访问的共享资源对象为同步监视器。语法格式如下:

    synchronized(obj) {

    ……

    }

    示例代码,模拟多个用户对同一个账户的取钱操作:

       1: //当多条线程修改同一共享数据时, 将涉及到线程安全
       2:     public void run() {
       3:         synchronized(account) {
       4:             //账户余额大于期望取到的金额
       5:             if (account.getBalance() >= drawAmount) {
       6:                 //吐抄
       7:                 System.out.println(getName() + "取钱成功,突出钞票:" + drawAmount);
       8:                 
       9:                 //修改余额
      10:                 account.setBalance(account.getBalance() - drawAmount);
      11:                 System.out.println("	余额为:" + account.getBalance());
      12:             }
      13:             else {
      14:                 System.out.println("余额不足,取钱失败!");
      15:             }
      16:         }
      17:         
      18:     }

    第二种:同步方法

    同步方法可以看作是同步代码块的变体,他不需要显示指定同步监视器,不过实则是把自己this当作同步监视器,因此而知同步方法是定义在要操作类的内部。示例代码,同样模拟取钱操作:

       1: package org.frzh.thread;
       2:  
       3: public class Account2 {
       4:     private String accountNo;
       5:     private double balance;
       6:     
       7:     public Account2() {}
       8:     public Account2(String accountNo, double balance) {
       9:         this.accountNo = accountNo;
      10:         this.balance = balance;
      11:     }
      12:     
      13:     public double getBalance() {
      14:         return this.balance;
      15:     }
      16:     //线程安全方法
      17:     public synchronized void draw(double drawAmount) {
      18:         //账户余额大于期望取到的金额
      19:         if (this.balance >= drawAmount) {
      20:             //吐抄
      21:             System.out.println(Thread.currentThread().getName() + "取钱成功,突出钞票:" + drawAmount);
      22:             
      23:             //修改余额
      24:             this.balance -= drawAmount;
      25:             System.out.println("	余额为:" + this.balance);
      26:         }
      27:         else {
      28:             System.out.println("余额不足,取钱失败!");
      29:         }
      30:     }
      31: }

    同步方法和同步代码库比较而言,同步方法更符合面向对象编程的思想。

    第三种:同步锁(Lock)

    同步锁是在线程访问共享资源时将资源锁定,此时不允许其他线程对共享资源的访问,操作完成之后再释放同步锁(且必须显示调用)。相比较同步代码块和同步方法而言,同步锁显得更加灵活,当然使用起来也是最容易出粗的。示例代码:

       1: package org.frzh.thread;
       2:  
       3: import java.util.concurrent.locks.ReentrantLock;
       4:  
       5: public class Account3 {
       6:     //定义所对象
       7:     private final ReentrantLock lock = new ReentrantLock();    //可重入锁
       8:     private String accountNo;
       9:     private double balance;
      10:     
      11:     public Account3() {}
      12:     public Account3(String accountNo, double balance) {
      13:         this.accountNo = accountNo;
      14:         this.balance = balance;
      15:     }
      16:     
      17:     public double getBalance() {
      18:         return this.balance;
      19:     }
      20:     
      21:     public void draw(double drawAmount) {
      22:         lock.lock();
      23:         try {
      24:             //账户余额大于期望取到的金额
      25:             if (this.balance >= drawAmount) {
      26:                 //吐抄
      27:                 System.out.println(Thread.currentThread().getName() + "取钱成功,突出钞票:" + drawAmount);
      28:                 
      29:                 //修改余额
      30:                 this.balance -= drawAmount;
      31:                 System.out.println("	余额为:" + this.balance);
      32:             }
      33:             else {
      34:                 System.out.println("余额不足,取钱失败!");
      35:             }
      36:         } finally {
      37:             lock.unlock();
      38:         }
      39:     }
      40: }
  • 相关阅读:
    hrbust 1788
    poj2299 ( bit )
    LA3027(并查集)
    hdu1166 (bit)
    hdu1598(并查集)
    cdoj1215 (并查集)
    hdu2643 ( 第二类斯特灵数 )
    hdu3625 ( 第一类斯特灵数 )
    Uva10066
    怎么处理sqlserver2017部署在winowsDocker上时区无法修改成功的方式,并且可以多创建新的容器调用简单的方式直接使用!
  • 原文地址:https://www.cnblogs.com/hgfrzh/p/3369706.html
Copyright © 2011-2022 走看看