Java银行取钱线程安全问题实例讲解
创始人
2024-12-22 17:40:50
0次

本文实例讲述了Java银行取钱线程安全问题。分享给大家供大家参考,具体如下:

一 定义一个账户类

public class Account{   // 封装账户编号、账户余额的两个成员变量   private String accountNo;   private double balance;   public Account(){}   // 构造器   public Account(String accountNo , double balance)   {      this.accountNo = accountNo;      this.balance = balance;   }   // 此处省略了accountNo和balance的setter和getter方法   // accountNo的setter和getter方法   public void setAccountNo(String accountNo)   {      this.accountNo = accountNo;   }   public String getAccountNo()   {      return this.accountNo;   }   // balance的setter和getter方法   public void setBalance(double balance)   {      this.balance = balance;   }   public double getBalance()   {      return this.balance;   }   // 下面两个方法根据accountNo来重写hashCode()和equals()方法   public int hashCode()   {      return accountNo.hashCode();   }   public boolean equals(Object obj)   {      if(this == obj)        return true;      if (obj !=null        && obj.getClass() == Account.class)      {        Account target = (Account)obj;        return target.getAccountNo().equals(accountNo);      }      return false;   }}

二 定义一个取钱线程

public class DrawThread extends Thread{   // 模拟用户账户   private Account account;   // 当前取钱线程所希望取的钱数   private double drawAmount;   public DrawThread(String name , Account account      , double drawAmount)   {      super(name);      this.account = account;      this.drawAmount = drawAmount;   }   // 当多条线程修改同一个共享数据时,将涉及数据安全问题。   public void run()   {      // 账户余额大于取钱数目      if (account.getBalance() >= drawAmount)      {        // 吐出钞票        System.out.println(getName()           + "取钱成功!吐出钞票:" + drawAmount);        try        {           Thread.sleep(1);        }        catch (InterruptedException ex)        {           ex.printStackTrace();        }        // 修改余额        account.setBalance(account.getBalance() - drawAmount);        System.out.println("\t余额为: " + account.getBalance());      }      else      {        System.out.println(getName() + "取钱失败!余额不足!");      }   }}

三 测试主类

public class DrawTest{   public static void main(String[] args)   {      // 创建一个账户      Account acct = new Account("1234567" , 1000);      // 模拟两个线程对同一个账户取钱      new DrawThread("甲" , acct , 800).start();      new DrawThread("乙" , acct , 800).start();   }}

四 运行

乙取钱成功!吐出钞票:800.0甲取钱成功!吐出钞票:800.0 余额为: 200.0 余额为: -600.0

五 说明

账户余额只有1000时取出1600,而且账户余额出现了负数,这部是银行希望看到的结果。

虽然上面程序是人为地使用Thread.sleep(1)来强制线程调度切换,但这种切换是完全可能发生的。

相关内容

热门资讯

空调连续工作多久需要停机休息 空调连续工作的时间取决于多个因素,包括空调的型号、功率、使用环境和维护情况等。一般来说,空调可以连续...
空调哪个符号是除湿的 空调除湿功能通常用一个水滴形状的符号表示。不同品牌和型号的空调遥控器可能会有所差异,但一般来说,除湿...
格力空调多长时间加一次氟利昂 1、一般情况下,空调对氟利昂的使用量是非常小的,所以在空调使用了四年左右的时候再考虑加也没问题。2、...
空调用多长时间需要加氟一次 一般情况下是五年。当出现以下这几种情况时,空调才需要加氟。1、空调的室内机和室外机各有两个接口,当接...
格调生活·C标思享荟:卡萨帝在... 9月12日的郑州龙湖金融岛,夜风轻拂,灯光璀璨。“C标时刻共传奇——卡萨帝思享荟暨20周年品牌盛典郑...
品牌价值破千亿、高端份额持续领... 9月12日,“C标时刻共传奇——卡萨帝思享荟暨20周年品牌盛典郑州站”在郑州龙湖金融岛举办。2026...
空调主板坏了修800还是换新的 空调主板坏了是修还是换新,需要考虑多个因素,以下是一些建议:1. 维修成本:如果维修费用较低,比如 ...
空调开多久需要休息多长时间 问题:空调开多久需要休息多长时间回答:1、在使用空调的过程中,一般空调开7~8个小时左右需要休息2~...
中央空调多长时间清洗一次 1、一般空调开机前清洗一次即可,空调开机中间时段再清洗一次,空调关机时清洗一次,这样比较合理。2、空...
中央空调氟利昂多久加一次 看空调制热和制冷程度,很多人的观点认为氟利昂必须一年放一次,其实这个观点是错误的,理解上面有点偏差,...