必须用 try-with-resources,因为 Connection、Statement、ResultSet 均实现 AutoCloseable,可确保异常或提前 return 时按逆序自动关闭,避免资源泄漏;JDBC 4.0+ 无需 Class.forName(),推荐 PreparedStatement 防 SQL 注入。

Java 中用 try-with-resources 查数据库,核心是让 Connection、Statement 和 ResultSet 都自动关闭,避免资源泄漏。它不是“额外功能”,而是 JDBC 资源管理的推荐写法。
为什么必须用 try-with-resources?
这三个对象都实现了 AutoCloseable 接口,手动 close 容易遗漏(比如查询中途抛异常,conn.close() 就根本不会执行)。而 try-with-resources 保证:无论是否异常、是否提前 return,所有声明在括号里的资源都会按逆序自动调用 close()。
标准查数据写法(带异常处理)
下面是一个安全、简洁、可直接运行的示例:
String url = "jdbc:mysql://localhost:3306/mydb?useSSL=false&serverTimezone=UTC";
String user = "root";
String password = "123456";
try (Connection conn = DriverManager.getConnection(url, user, password);
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery("SELECT id, name FROM users")) {
while (rs.next()) {
int id = rs.getInt("id");
String name = rs.getString("name");
System.out.println(id + ": " + name);
}
} catch (SQLException e) {
e.printStackTrace();
}
说明:
立即学习“Java免费学习笔记(深入)”;
- 三个资源按顺序声明,关闭时会反向执行:先
rs.close(),再stmt.close(),最后conn.close() - 即使
rs.next()循环中抛出异常,rs和stmt仍会被关闭 - JDBC 4.0+ 不需要
Class.forName(),驱动会自动加载
用 PreparedStatement 更安全(防 SQL 注入)
如果查询带参数(比如根据姓名查用户),应优先用 PreparedStatement:
String sql = "SELECT id, name FROM users WHERE age > ?";
try (Connection conn = DriverManager.getConnection(url, user, password);
PreparedStatement pstmt = conn.prepareStatement(sql)) {
pstmt.setInt(1, 18); // 设置参数
try (ResultSet rs = pstmt.executeQuery()) {
while (rs.next()) {
System.out.println(rs.getString("name"));
}
}
} catch (SQLException e) {
e.printStackTrace();
}
注意:ResultSet 在内部 try 中声明,这样它能随 pstmt 的生命周期被精准管理;外部 try 只管连接和语句。
常见误区提醒
这些做法容易出问题,要避开:
- 在一个
Statement上多次调用executeQuery():后一次会自动关闭前一次的ResultSet,导致IllegalStateException - 把
ResultSet提到 try 括号外:失去自动关闭保障,变成手动管理 - 用连接池时误以为“不用关”:逻辑连接(
Connection)仍需close(),这是归还连接给池的关键动作,try-with-resources正好完成这件事


















