Java案例分析

【案例8-3】 模拟银行存取钱

2024-10-25 46 0

简介 1.任务描述 在银行办理业务时,通常银行会开多个窗口,客户排队等候,窗口办理完业务,会呼叫下一个用户办理业务。本案例要求编写一个程序模拟银行存取钱业务办理。假如有两个用户在存取钱,两个用户分别操作各自的账户,并在控制台打印存取钱的数量以及账户的余额。

【案例8-3  模拟银行存取钱

【案例介绍】

  1.任务描述

在银行办理业务时,通常银行会开多个窗口,客户排队等候,窗口办理完业务,会呼叫下一个用户办理业务。本案例要求编写一个程序模拟银行存取钱业务办理。假如有两个用户在存取钱,两个用户分别操作各自的账户,并在控制台打印存取钱的数量以及账户的余额。

2.运行结果

运行结果如图8-1所示。

upfile

8-1 运行结果

【案例目标】

l  学会分析“模拟银行存取钱功能任务实现的逻辑思路。

l  能够独立完成“模拟银行存取钱功能程序的源代码编写、编译以及运行。

l  通过存取款线程理解多线程安全问题的发生原因,并掌握如何解决多线程安全问题。

【案例思路】

(1)     通过任务描述和运行结果可以看出,该任务需要使用多线程的相关知识来实现。由于两个用户操作各自的账户,因此我们需要创建两个线程完成每个用户的操作。这里我们使用实现Runnable接口的方法来创建线程。

(2)     既然是储户去银行存款,那么可以得出该任务会涉及到三个类,分别是银行类、储户类和测试类。

(3)     定义一个实体类作为账务的集合,包括用户名、登录名、登录密码、钱包、取钱时间和存钱时间等字段。

(4)     在银行类中需要定义一个账户的实体类、一个存钱的方法、一个取钱的方法、查询余额的方法和获取当前用户的方法。获取当前用户方法需要使用synchronized线程锁判断是哪一位用户,在存钱和取钱的方法中先调用获取用户方法判断操作者,再进行存取钱操作,需要注意的是在进行取钱操作时,需要判断余额是否大于需要取的钱数。

(5)     在测试类中使用for循环调用线程模拟用户存取钱操作。

【案例代码】

(1)     创建用户类

 定义一个用户的类,根据用户实现多人同时存取钱功能,如文件8-1所示。

文件8-1  User.java

 1   package chapter0803;

 2   import java.util.Date;

 3   public class User {

 4        private String u_name;//用户名

 5           private String u_login_name;//登录名 卡的id

 6           private String u_login_pwd;//登录密码

 7           private String u_wallet;//钱包

 8           private Date  draw_money_time;//取钱时间

 9           private Date  save_money_time;//存钱时间

 10          public User(){}

 11          public User(String u_name, String u_login_name, String u_login_pwd,

 12                        String u_wallet) {

 13              this.u_name = u_name;

 14              this.u_login_name = u_login_name;

 15              this.u_login_pwd = u_login_pwd;

 16              this.u_wallet = u_wallet;

 17          }

 18          public User(String u_name, String u_login_name, String u_login_pwd,

 19               String u_wallet, Date draw_money_time, Date save_money_time) {

 20              this.u_name = u_name;

 21              this.u_login_name = u_login_name;

 22              this.u_login_pwd = u_login_pwd;

 23              this.u_wallet = u_wallet;

 24              this.draw_money_time = draw_money_time;

 25              this.save_money_time = save_money_time;

 26          }

 27          public String getU_name() {

 28              return u_name;

 29          }

 30          public void setU_name(String u_name) {

 31              this.u_name = u_name;

 32          }

 33          public String getU_login_name() {

 34              return u_login_name;

 35          }

 36          public void setU_login_name(String u_login_name) {

 37              this.u_login_name = u_login_name;

 38          }

 39          public String getU_login_pwd() {

 40              return u_login_pwd;

 41          }

 42          public void setU_login_pwd(String u_login_pwd) {

 43              this.u_login_pwd = u_login_pwd;

 44          }

 45          public String getU_wallet() {

 46              return u_wallet;

 47          }

 48          public void setU_wallet(String u_wallet) {

 49              this.u_wallet = u_wallet;

 50          }

 51          public Date getDraw_money_time() {

 52              return draw_money_time;

 53          }

 54          public void setDraw_money_time(Date draw_money_time) {

 55              this.draw_money_time = draw_money_time;

 56          }

 57          public Date getSave_money_time() {

 58              return save_money_time;

 59          }

 60          public void setSave_money_time(Date save_money_time) {

 61              this.save_money_time = save_money_time;

 62          }

 63      }

(2)     创建银行业务类

 定义一个业务类,实现用户的存取钱功能,如文件8-2所示。

文件8-2 Bank.java

 1   package chapter0803;

 2   import java.math.BigDecimal;

 3   import java.text.SimpleDateFormat;

 4   import java.util.ArrayList;

 5   import java.util.Date;

 6   import java.util.List;

 7   public class Bank {

 8         private List<User> userList=new ArrayList<User>();

 9           public  Bank(List<User> userList) {

 10               this.userList = userList;

 11          }

 12          public  List<User> getUserList() {

 13              return userList;

 14          }

 15          public void setUserList(List<User> userList) {

 16              this.userList = userList;

 17          }

 18          //存钱

 19          public Boolean saveMoney(String card,String pwd,String moneyNum){

 20              User u=getUserByCard(card);

 21              synchronized (Bank.class) {

 22              if (u.getU_login_name().equals(card) &&

 23                    u.getU_login_pwd().equals(pwd)) {

 24                          BigDecimal oldData=new BigDecimal(u.getU_wallet());

 25                          BigDecimal money=new BigDecimal(moneyNum);

 26                          u.setU_wallet(oldData.add(money).toString());

 27                          u.setSave_money_time(new Date());

 28            System.out.println(Thread.currentThread().getName()+"存钱

 29            ---->"+u.getU_name()+""+new SimpleDateFormat("yyyy-MM-dd

 30            HH:mm:ss").format(u.getSave_money_time())+"["+moneyNum+"]钱,余额:

 31            "+u.getU_wallet());

 32                          return true;

 33                      }

 34                  }

 35              System.out.println(getUserByCard(card).getU_name()+"存钱失败");

 36            return false;

 37          }

 38          //取钱

 39          public Boolean getMoney(String card,String pwd,String moneyNum){

 40              User u=getUserByCard(card);

 41              synchronized (Bank.class) {

 42              if (u!=null && u.getU_login_name().equals(card) &&

 43                   u.getU_login_pwd().equals(pwd)) {

 44                      BigDecimal oldData=new BigDecimal(u.getU_wallet());

 45                      BigDecimal money=new BigDecimal(moneyNum);

 46                      if(oldData.compareTo(money)>=0){

 47                       u.setU_wallet(oldData.subtract(money).toString());

 48                       u.setDraw_money_time(new Date());

 49                System.out.println(Thread.currentThread().getName()+"取钱

 50                ---->"+u.getU_name()+""+new SimpleDateFormat("yyyy-MM-dd

 51              HH:mm:ss").format(u.getDraw_money_time())+"["+moneyNum+"]

 52             ,余额:"+u.getU_wallet());

 53                              return true;

 54                          }else {

 55                  System.out.println(getUserByCard(card).getU_name()+"

 56                                        要取["+moneyNum+"],但余额不足");

 57                              return false;

 58                          }

 59                      }

 60                  }

 61              System.out.println(card+"取钱失败");

 62              return false;

 63          }

 64          //查询余额

 65          public String balanceEnquiry(String card,String pwd){

 66              for(User u :this.userList){

 67                  if(u.getU_login_name().equals(card)&&

 68                      u.getU_login_pwd().equals(pwd)){

 69                   System.out.println(Thread.currentThread().getName()+":"

 70                                       +u.getU_name()+"余额:"+u.getU_wallet());

 71                      return u.getU_wallet();

 72                  }

 73              }

 74              System.out.println(Thread.currentThread().getName()+":"+card+"

 75                                     操作失败");

 76              return null;

 77          }

 78         //获取当前用户

 79          public synchronized User getUserByCard(String card){

 80              for(User u :this.userList){

 81                  if(u.getU_login_name().equals(card)){

 82                      return u;

 83                  }

 84              }

 85              return null;

 86          }

 87          public void delayTime(Integer nim){

 88              try {

 89                  Thread.sleep(nim);

 90              } catch (InterruptedException e) {

 91                  e.printStackTrace();

 92              }

 93          }

 94      }

(3)     创建测试类

 定义测试类,在类中创建客户对象,并创建和开启线程执行存取钱操作,如文件8-3所示。

 1   package chapter0803;

 2   import java.util.ArrayList;

 3   import java.util.List;

 4   public class BankText {

 5         public static void main(String[] args) throws Exception {

 6               User u = new User("张三", "132466", "123", "100");

 7               User uu = new User("李四", "4600882", "123", "0");

 8               List<User> list = new ArrayList<User>();

 9               list.add(u);

 10              list.add(uu);

 11              final Bank atm = new Bank(list);//初始化数据 模拟

 12              Thread t = new Thread() {

 13                  public void run() {

 14   

 15                      for (int i = 0; i < 10; i++) {

 16                          atm.saveMoney("132466", "123", "12");

 17                          atm.delayTime(250);

 18                          atm.getMoney("4600882", "123", "14");

 19                          atm.delayTime(250);

 20                      }

 21   

 22                  }

 23              };

 24              Thread tt = new Thread() {

 25                  public void run() {

 26   

 27                      for (int i = 0; i < 10; i++) {

 28                          atm.getMoney("132466", "123", "2");

 29                          atm.delayTime(250);

 30                          atm.saveMoney("4600882", "123", "12");

 31                          atm.delayTime(250);

 32                      }

 33                  }

 34              };

 35              t.start();

 36              tt.start();

 37          }

 38      }

 


点赞 0

文章评论

欢迎您:

阿文博客

人生的价值,并不是用时间,而是用深度量去衡量的。——列夫·托尔斯泰

69 文章 1879 浏览 0 评论