如何根据用户输入创建对应账户对象以避免重复编写业务方法?
解决方案
完全可以实现,核心是利用Java多态特性抽离重复逻辑,不需要为两类账户单独编写相同的业务代码,具体优化步骤如下:
步骤1:调整Bank类的成员变量与方法参数
移除Bank类中写死的DepositAccount account成员变量,将账户实例改为方法入参传入,同时增加文件名后缀参数区分不同账户的存储文件。另外原来作为成员变量的交易列表transactionsToAdd会导致多调用场景下的数据污染,改成方法内局部变量更合理。
步骤2:合并重复的账户管理方法
将两套几乎完全一致的账户管理逻辑合并为一个通用方法,根据传入的后缀动态生成文件名,根据传入的账户实例执行对应逻辑:
public class Bank { ScannerClass scanner = new ScannerClass(); DateManager dateManager = new DateManager(); Writer writer = new Writer(); Reader reader = new Reader(); // 通用账户管理方法 public void ManageAccount(String name, BankAccount account, String fileSuffix) { // 每次调用初始化独立的交易列表,避免数据互相干扰 List<Transaction> transactionsToAdd = new ArrayList<Transaction>(); try { // 动态生成文件名 String baseFileName = name + fileSuffix; File myObj = new File(baseFileName + ".txt"); if (myObj.createNewFile()) { File myTransactionObj = new File(baseFileName + "Transactions.txt"); myTransactionObj.createNewFile(); writer.SingleLineWriter(baseFileName, "0"); } else { account.setName(name); String line = reader.SingleLineRead(baseFileName); double balance = Double.parseDouble(line); // 把账户实例、基础文件名、交易列表传入后续业务方法 double newBalance = ManageBank(balance, account, baseFileName, transactionsToAdd); writer.BalanceAppender(newBalance, baseFileName); } } catch (IOException e) { System.out.println("发生错误"); e.printStackTrace(); } } // 调整ManageBank的入参,接收外部传入的账户、文件名和交易列表 public double ManageBank(double balance, BankAccount account, String baseFileName, List<Transaction> transactionsToAdd) throws IOException { boolean quit = false; List<String> transactions = reader.readPreviousTransactions(baseFileName); do { int userChoice = scanner.InitialChoiceScanner(); switch (userChoice) { case 1: double amount = scanner.DepositScanner(); balance = account.Deposit(balance, amount); System.out.print("你的新余额为:" + balance); String depositFullDate = dateManager.getDateAsString(); Transaction depositTransaction = new Transaction("存款", amount, depositFullDate); transactionsToAdd.add(depositTransaction); break; case 2: double withdrawAmount = scanner.WithdrawScanner(); if (withdrawAmount > balance) { System.out.println("抱歉,余额不足"); break; } balance = account.Withdraw(balance, withdrawAmount); System.out.print("你的新余额为:" + balance); String withdrawFullDate = dateManager.getDateAsString(); Transaction withdrawTransaction = new Transaction("取款", withdrawAmount, withdrawFullDate); transactionsToAdd.add(withdrawTransaction); break; case 3: System.out.print("你的当前余额为:" + balance); break; case 4: writer.displayStatement(baseFileName); break; case 0: quit = true; break; default: System.out.println("请选择有效选项"); break; } System.out.println(); } while (!quit); List<Transaction> parsedTransactions = writer.parseStringToTransaction(transactions); for (Transaction transaction : parsedTransactions) { transactionsToAdd.add(transaction); } writer.transactionWriter(transactionsToAdd, baseFileName); System.out.println("感谢使用银行服务!"); return balance; } }
步骤3:按账户类型调用通用方法
用户选择账户类型后,创建对应实例传入通用方法即可,不需要再单独编写两套业务逻辑:
// 调用存款账户管理 Bank bank = new Bank(); BankAccount depositAccount = new DepositAccount(); bank.ManageAccount("张三", depositAccount, ""); // 调用储蓄账户管理 BankAccount savingsAccount = new SavingsAccount(); bank.ManageAccount("张三", savingsAccount, "-Savings");
后续扩展建议
如果后续两类账户需要新增差异化逻辑,直接在对应的SavingsAccount或DepositAccount类中重写Deposit、Withdraw等方法即可,上层的通用管理逻辑不需要修改,符合面向对象的开闭原则。
内容的提问来源于stack exchange,提问作者Connor Gill
相关产品推荐
相关产品推荐

