勇闯前后端:Java 基础语法 + ATM 同步实现
勇闯前后端:Java 基础语法 + ATM 同步实现
变量、数组、集合(ArrayList, HashMap)
知识点讲解
- 变量(variable):Java 是强类型语言,变量声明需要类型。局部变量必须在使用前初始化;成员变量有默认值。
- 基本类型与引用类型:
int, long, double, boolean是基本类型;String, Integer, ArrayList<T>是引用类型。 - 数组(array):定长、零基索引。语法:
int[] a = new int[5];或int[] b = {1,2,3};。 - 集合(Collections):Java 提供
List,Map等接口。常用实现:ArrayList(动态数组)、HashMap(键值对,无序、基于哈希)。 - 自动装箱/拆箱:
Integer与int之间的自动转换,但注意==比较包装类和基本类型的陷阱。
我们可以试一下:
import java.util.*;public class Day15Examples {public static void main(String[] args) {// 变量double balance = 1000.0;// 数组int[] history = {100, -50, 200};// ArrayListArrayList<String> names = new ArrayList<>();names.add("Alice");names.add("Bob");// HashMapHashMap<String, Double> users = new HashMap<>();users.put("Alice", 1000.0);users.put("Bob", 500.0);System.out.println("Alice balance: " + users.get("Alice"));}
}
练习题
- 写一个方法,接受
ArrayList<Integer>,返回最大值(若列表为空抛出IllegalArgumentException)。 - 使用
HashMap<String, Double>模拟 3 个用户余额,写方法从 Map 中按用户名取余额并格式化输出"Alice: 1000.00"。
参考答案(简要)
public static int max(ArrayList<Integer> list) {if (list == null || list.isEmpty()) throw new IllegalArgumentException("empty");int m = list.get(0);for (int v : list) m = Math.max(m, v);return m;
}
public static String fmtBalance(HashMap<String, Double> m, String user) {Double b = m.get(user);return String.format("%s: %.2f", user, b == null ? 0.0 : b);
}
函数与类的定义
- 类(class)与对象(object):类是模板,对象是实例。成员变量(字段)和方法定义对象的状态与行为。
- 方法(method)签名:返回类型、方法名、参数列表。重载是方法名相同但参数不同。
- 构造器(constructor):用于初始化对象。若不定义,编译器提供默认无参构造器。
- 访问修饰符:
public,protected,private, package-private(默认)。封装(encapsulation)通过private字段 +publicgetter/setter 实现。
public class Account {private double balance;public Account(double initial) {this.balance = initial;}public double getBalance() { return balance; }public void deposit(double amount) {if (amount < 0) throw new IllegalArgumentException("amount must be >= 0");balance += amount;}public void withdraw(double amount) {if (amount < 0) throw new IllegalArgumentException("amount must be >= 0");if (amount > balance) throw new IllegalArgumentException("insufficient funds");balance -= amount;}
}
练习题
- 编写
User类,字段:String username; Account account;,写构造器和toString()。 - 写静态工具方法
transfer(Account from, Account to, double amount),在from中减,在to中加(不做线程同步,简单版本)。
参考答案(简要)
public class User {private String username;private Account account;public User(String username, Account account) {this.username = username;this.account = account;}@Overridepublic String toString() {return username + ": " + account.getBalance();}
}
public static void transfer(Account from, Account to, double amount) {from.withdraw(amount);to.deposit(amount);
}
封装、继承与接口(理论 + 简单代码)
- 封装(Encapsulation):把实现细节隐藏在类中,暴露必要的接口(getter/setter)。优点:维护性和安全性更高。
- 继承(Inheritance):子类继承父类的字段与方法。使用
extends。注意 Java 的单继承限制(类只能继承一个类)。 - 接口(Interface):定义行为契约,类通过
implements实现。Java 8+ 支持接口默认方法和静态方法。 - 面向接口编程(Program to an interface):使用接口作为变量类型可以提高灵活性。
public interface Transaction {void execute();
}public class DepositTransaction implements Transaction {private Account acc;private double amount;public DepositTransaction(Account acc, double amount) {this.acc = acc; this.amount = amount;}public void execute() { acc.deposit(amount); }
}public class SavingsAccount extends Account {private double interestRate;public SavingsAccount(double init, double rate) {super(init);this.interestRate = rate;}public void applyInterest() {deposit(getBalance() * interestRate);}
}
- 写一个
Transaction实现TransferTransaction,在execute()中把金额从一个账户转到另一个账户。 - 设计一个
AuditableAccount(继承Account),在deposit/withdraw中打印日志(或记录到列表)。
参考答案(简要)
public class TransferTransaction implements Transaction {private Account from, to; private double amount;public TransferTransaction(Account from, Account to, double amount) {this.from = from; this.to = to; this.amount = amount;}public void execute() {from.withdraw(amount);to.deposit(amount);}
}
public class AuditableAccount extends Account {private List<String> logs = new ArrayList<>();public AuditableAccount(double init) { super(init); }@Override public void deposit(double amount) {super.deposit(amount);logs.add("deposit:"+amount);}@Override public void withdraw(double amount) {super.withdraw(amount);logs.add("withdraw:"+amount);}
}
实现 ATM v0.1(Java 版)
目标与分解
- 功能:登录(按用户名)、查询余额、存款、取款、退出、简单转账(可选)
- 数据结构:
HashMap<String, Account>管理账户 - 用户体验:命令行菜单循环
- 线程安全(同步):示范
synchronized方法或使用ReentrantLock,以防未来多线程并发访问账户
import java.util.*;/*** Simple thread-safe bank account.*/
class Account {private double balance;public Account(double initial) { this.balance = initial; }/*** Deposit into account (thread-safe).*/public synchronized void deposit(double amount) {if (amount < 0) throw new IllegalArgumentException("amount must be >= 0");balance += amount;}/*** Withdraw from account (thread-safe).*/public synchronized void withdraw(double amount) {if (amount < 0) throw new IllegalArgumentException("amount must be >= 0");if (amount > balance) throw new IllegalArgumentException("insufficient funds");balance -= amount;}public synchronized double getBalance() { return balance; }
}/** Simple user holder */
class User {private final String username;private final Account account;public User(String username, Account account) {this.username = username; this.account = account;}public String getUsername() { return username; }public Account getAccount() { return account; }
}/** ATM controller */
class ATM {private final HashMap<String, User> users = new HashMap<>();private User current = null;private final Scanner sc = new Scanner(System.in);public ATM() {// sample datausers.put("Alice", new User("Alice", new Account(1000.0)));users.put("Bob", new User("Bob", new Account(500.0)));}public void run() {while (true) {if (current == null) showLoginMenu();else showUserMenu();}}private void showLoginMenu() {System.out.println("--- ATM ---");System.out.print("Enter username (or 'exit'): ");String line = sc.nextLine().trim();if (line.equalsIgnoreCase("exit")) { System.exit(0); }if (users.containsKey(line)) {current = users.get(line);System.out.println("Login success: " + current.getUsername());} else {System.out.println("Unknown user. Try again.");}}private void showUserMenu() {System.out.println("\n--- Menu for " + current.getUsername() + " ---");System.out.println("1) Query balance");System.out.println("2) Deposit");System.out.println("3) Withdraw");System.out.println("4) Logout");System.out.print("Choose: ");String choice = sc.nextLine().trim();try {switch (choice) {case "1":System.out.printf("Balance: %.2f\n", current.getAccount().getBalance());break;case "2":double d = readDouble("Deposit amount: ");current.getAccount().deposit(d);System.out.println("Deposited.");break;case "3":double w = readDouble("Withdraw amount: ");current.getAccount().withdraw(w);System.out.println("Withdrawn.");break;case "4":current = null; System.out.println("Logged out.");break;default:System.out.println("Invalid option.");}} catch (IllegalArgumentException e) {System.out.println("Error: " + e.getMessage());}}private double readDouble(String prompt) {while (true) {System.out.print(prompt);String line = sc.nextLine().trim();try { return Double.parseDouble(line); }catch (NumberFormatException e) { System.out.println("Please enter a valid number."); }}}
}public class Main {public static void main(String[] args) {ATM atm = new ATM();atm.run();}
}
