必须用ArrayList而非ArrayList管理图书,因Book类封装标题、作者、ISBN等属性,支持按属性筛选、状态修改及序列化持久化,避免数据丢失。

用 ArrayList 存 Book 对象而不是 String
很多人一开始把书名当 String 存进 ArrayList,结果后续没法查作者、ISBN 或借阅状态。必须定义 Book 类,再用 ArrayList 管理:
public class Book {
private String title;
private String author;
private String isbn;
private boolean isBorrowed;
public Book(String title, String author, String isbn) {
this.title = title;
this.author = author;
this.isbn = isbn;
this.isBorrowed = false;
}
// getter/setter 略
}
-
ArrayList支持按属性筛选(比如找所有“刘慈欣”的书),ArrayList只能模糊匹配标题 - 别忘了重写
Book的equals()和hashCode()——否则list.remove(book)可能失效 - 如果后期要按 ISBN 快速查找,
HashMap比遍历ArrayList更合适
增删改查操作别绕开 for 循环直接调 API
初学者常误以为 list.stream().filter(...).findFirst() 是唯一解法,但简单系统里手写 for 更直观、易调试、不隐式抛 NullPointerException:
public Book findBookByIsbn(String isbn) {
for (Book book : books) {
if (book.getIsbn().equals(isbn)) {
return book;
}
}
return null;
}
- 用
stream()前先确认 JDK 版本 ≥ 8,且项目没禁用函数式编程 -
list.removeIf(b -> b.getIsbn().equals(isbn))会直接删对象,不是“找出来再删”,容易误操作 - 修改某本书的借阅状态,别新建
Book替换原对象——引用没变,但list.indexOf()会失效;直接调book.setBorrowed(true)
控制台输入中文时 Scanner.nextLine() 吃掉回车的问题
用 Scanner 录入书名、作者时,如果前面用了 nextInt() 或 nextDouble(),紧接着的 nextLine() 会读到空字符串——因为前一个方法没消费换行符:
- 统一用
nextLine()读所有输入,数字再转:Integer.parseInt(scanner.nextLine().trim()) - 或者在
nextInt()后加一句scanner.nextLine()清缓冲区 - 避免用
next()读书名——遇到“三体 第一部”这种带空格的就只读到“三体”
退出系统前不保存数据,关掉程序就丢书
内存里的 ArrayList 不会自动落盘。最简方案是序列化到文件(别急着上数据库):
立即学习“Java免费学习笔记(深入)”;
try (ObjectOutputStream oos = new ObjectOutputStream(
new FileOutputStream("books.dat"))) {
oos.writeObject(books);
} catch (IOException e) {
System.err.println("保存失败:" + e.getMessage());
}
- 要求
Book实现Serializable接口,且所有字段可序列化(如transient标记的不会存) - 启动时用
ObjectInputStream反序列化加载;首次运行文件不存在就 catchFileNotFoundException并初始化空列表 - 别用
PrintWriter写纯文本——没有类型信息,下次读进来还得手动拆字段、new 对象
集合本身只是容器,真正让系统“记住”书的,是你对对象生命周期和数据持久化的处理方式。很多 bug 不出在逻辑,而出现在没意识到 ArrayList 里的对象只活在本次 JVM 进程里。










