完整教程:JDBC是Java连接数据库的标准接口,通过统一API屏蔽不同数据库差异。其核心包括DriverManager管理驱动、Connection建立连接、Statement执行SQL及ResultSet处理结果集。学习重点应掌握基础操作(增删改查)、事务管理(commit/rollback)、防SQL注入(PreparedStatement)及批处理优化。此外需理解连接池原理(如Hi
day03 jdbc
1.jdbc
1.1jdbc的原理
JDBC(Java Database Connectivity)是 Java 提供的一套访问关系型数据库的标准接口,它的核心作用是作为 Java 程序与数据库之间的 “桥梁”,屏蔽不同数据库的底层差异,让 Java 开发者通过统一的 API 操作各种数据库(如 MySQL、Oracle 等)。
核心原理可从 3 个层面理解:
- 接口与实现分离:JDBC 定义了一套接口(如
Driver、Connection、Statement等),具体的实现由数据库厂商提供(即 “JDBC 驱动”,如 MySQL 的com.mysql.cj.jdbc.Driver)。开发者无需关心数据库底层细节,只需调用接口方法即可。- 核心组件
DriverManager:管理数据库驱动,负责根据 URL 获取数据库连接;Connection:代表与数据库的连接(会话),是所有操作的基础;Statement/PreparedStatement:执行 SQL 语句的对象(PreparedStatement支持预编译,可防止 SQL 注入);ResultSet:存储 SQL 查询的结果集。
- 工作流程:
① 加载数据库驱动(如Class.forName("com.mysql.cj.jdbc.Driver"));
② 通过DriverManager获取Connection连接;
③ 创建Statement对象并执行 SQL;
④ 处理ResultSet结果集;
⑤ 关闭资源(连接、Statement 等)。
jdbc学到什么程度为以后找工作做铺垫?
二、进阶特性:体现 “实用性” 的关键能力
企业更看重 “能解决实际问题” 的能力,这部分是区分 “会用” 和 “用得好” 的核心。
事务管理
理解 JDBC 事务的默认行为(自动提交autoCommit=true),能手动控制事务:
conn.setAutoCommit(false)关闭自动提交;conn.commit()提交事务、conn.rollback()回滚(结合try-catch,异常时回滚);
- 了解事务隔离级别(
conn.setTransactionIsolation(Connection.TRANSACTION_READ_COMMITTED)),能解释不同级别解决的问题(脏读、不可重复读、幻读)。
防 SQL 注入与预编译
- 明确
Statement和PreparedStatement的区别:PreparedStatement通过预编译 SQL 模板、参数占位符(?)避免 SQL 注入,必须掌握其参数设置方法(setInt、setString等)。批处理(Batch)
掌握大量数据插入 / 更新时的优化:ps.addBatch()添加批处理命令,ps.executeBatch()执行,减少数据库交互次数,提升效率。异常处理
能处理常见SQLException(如连接失败、SQL 语法错误、主键冲突),并根据异常信息排查问题(例如通过getErrorCode()判断数据库特定错误)。三、底层原理:面试高频考点,体现 “深度”
企业(尤其是中大厂)会考察对底层的理解,这是理解框架(如 MyBatis)的基础。
- JDBC 工作原理
- 驱动(Driver)的作用:不同数据库(MySQL、Oracle)的驱动实现
java.sql.Driver接口,DriverManager通过扫描META-INF/services/java.sql.Driver文件加载驱动;- 连接(Connection)的本质:是客户端与数据库服务器的 TCP 连接封装;
- 结果集(ResultSet)的遍历机制:游标(Cursor)的移动原理,
TYPE_FORWARD_ONLY(只能向前)、TYPE_SCROLL_INSENSITIVE(可滚动)等类型的区别。
- 连接池的必要性与基础
- 理解
DriverManager直接获取连接的缺陷(创建销毁成本高、并发性能差);- 掌握常用连接池(HikariCP、Druid)的基本使用:配置连接池参数(初始连接数、最大连接数、超时时间),通过连接池获取
Connection(而非直接用DriverManager)。四、实际场景:结合项目的 “落地能力”
企业需要 “能干活” 的人,需结合实际开发场景理解 JDBC 的应用与局限。
- 性能优化
- 避免频繁创建连接(用连接池);
- 大结果集处理:设置
rs.setFetchSize(n)控制每次从数据库拉取的行数,避免内存溢出;- 读写分离场景下,通过 JDBC 连接不同数据源(主库写、从库读)。
- 与框架的关联
- 知道 JDBC 的 “繁琐性”(重复代码多),理解 MyBatis 等 ORM 框架的价值(自动映射、简化 SQL 操作);
- 了解 Spring 的
JdbcTemplate:它是对 JDBC 的轻量封装,能说出其核心优势(简化资源管理、提供模板方法)。
- 特殊数据类型处理
能处理 BLOB(二进制,如图片)、CLOB(大文本)类型:用setBlob()/getBlob()、setClob()/getClob()操作。总结:达到这些标准,足以应对多数岗位
- 初级岗:熟练掌握 “核心基础 + 事务 + 防注入”,能独立写 JDBC 操作代码,理解连接池的作用;
- 中级岗:在初级基础上,掌握 “批处理 + 连接池配置 + 性能优化”,能解释 JDBC 原理,结合框架(如 MyBatis)分析问题。
JDBC 是 Java 操作数据库的基石,即使实际工作中多用框架,但其原理和思想(如事务、连接管理)贯穿始终。掌握到上述程度,既能通过笔试(写 JDBC 代码),也能应对面试(原理问答),为找工作打下扎实基础。
1.2jdbc的代码实现
增
public static void main(String[] args) throws SQLException, ClassNotFoundException {
//1.加载驱动
Class.forName("com.mysql.cj.jdbc.Driver");
//2.获取连接
Connection connection = DriverManager.getConnection("jdbc:mysql://localhost:3306/qindu?serverTimezone=GMT","root","123456");
//3.拼写sql ?代表数据的占位符
String sql="insert into stu(stu_name,stu_hobby,stu_nickname) values(?,?,?)";
//4.获取sql的执行对象(preparedStatement)
PreparedStatement preparedStatement = connection.prepareStatement(sql);
//5.给占位符填写数据
//preparedStatement.setInt(填写数据为int);
preparedStatement.setString(1,"张倩娜");
preparedStatement.setString(2,"跑步");
preparedStatement.setString(3,"姬夜");
//6.执行sql语句
//执行增,删,改sql语句:executeUpdate()
//执行查询sql语句,executeQuery()
int row = preparedStatement.executeUpdate();
if(row>
0){
System.out.println("新增成功");
}else{
System.out.println("新增失败");
}
//7.回收资源,注意:先用后关,后用先关
preparedStatement.close();
connection.close();
}
删
public static void main(String[] args) throws SQLException, ClassNotFoundException {
//1.加载驱动
Class.forName("com.mysql.cj.jdbc.Driver");
//2.获取连接
Connection connection = DriverManager.getConnection("jdbc:mysql://localhost:3306/qindu?serverTimezone=GMT","root","123456");
connection.setAutoCommit(false);
//关闭事务提交
//3.拼写sql?代表数据的占位符
String sql="delete from stu where stu_id=?";
//4.获取sql的执行对象(preparedStatement)
PreparedStatement preparedStatement = connection.prepareStatement(sql);
//5.给占位符填写数据
//preparedStatement.setInt(填写数据为int);
preparedStatement.setInt(1,2);
//6.执行sql语句
//执行增,删,改sql语句:executeUpdate()
//执行查询sql语句,ex
int row = preparedStatement.executeUpdate();
if(row>
0){
System.out.println("删除成功");
connection.commit();
//手动提交
}else{
System.out.println("删除失败");
}
//7.回收资源,注意:先用后关,后用先关
preparedStatement.close();
connection.close();
}
改
public static void main(String[] args) throws SQLException, ClassNotFoundException {
//1.加载驱动
Class.forName("com.mysql.cj.jdbc.Driver");
//2.获取连接
Connection connection = DriverManager.getConnection("jdbc:mysql://localhost:3306/qindu?serverTimezone=GMT","root","123456");
//3.拼接sql ?代表数据的占位符
String sql="update stu set stu_name=?,stu_hobby=?,stu_nickname=? where stu_id=?";
//4.获取sql语句的执行对象
PreparedStatement preparedStatement = connection.prepareStatement(sql);
//5.给占位符填写数据
preparedStatement.setString(1,"迪丽热巴");
preparedStatement.setString(2,"演习");
preparedStatement.setString(3,"巴巴");
preparedStatement.setInt(4,1);
//6.执行sql语句
//执行增,删,改用executeUpdate()
//执行查询,用executeQuery()
int row = preparedStatement.executeUpdate();
if(row>
0){
System.out.println("修改成功");
}else{
System.out.println("修改失败");
}
preparedStatement.close();
connection.close();
}
查
public static void main(String[] args) throws ClassNotFoundException, SQLException {
//1.加载驱动
Class.forName("com.mysql.cj.jdbc.Driver");
//2.获取连接
Connection connection =
DriverManager.getConnection("jdbc:mysql://localhost:3306/qindu?serverTimezone=GMT", "root", "123456");
//3.拼写sql?代表数据的占位符
String sql = "select * from stu";
//4.获取sql的执行对象preparedStatement
PreparedStatement preparedStatement = connection.prepareStatement(sql);
//6.执行sql语句
ResultSet resultSet = preparedStatement.executeQuery();
List<
Student> list = new ArrayList<
>();
while (resultSet.next()) {
int id = resultSet.getInt("stu_id");
String name = resultSet.getString("stu_name");
String hobby = resultSet.getString("stu_hobby");
String nick = resultSet.getString("stu_nickname");
Student student = new Student(id, name, hobby, nick);
list.add(student);
}
//7.打印
System.out.println(list);
//8.回收资源
resultSet.close();
preparedStatement.close();
connection.close();
}
public static void main(String[] args) throws ClassNotFoundException, SQLException {
//1.加载驱动
Class.forName("com.mysql.cj.jdbc.Driver");
//2.获取连接
Connection connection =
DriverManager.getConnection("jdbc:mysql://localhost:3306/qindu?serverTimezone=GMT", "root", "123456");
//3.拼写sql?代表数据的占位符
String sql = "select stu_name,stu_nickname from stu where stu_id=?";
//4.获取sql的执行对象preparedStatement
PreparedStatement preparedStatement = connection.prepareStatement(sql);
//5.给占位符填写数据
//查id为2的数据
preparedStatement.setInt(1,3);
//6.执行sql语句
ResultSet resultSet = preparedStatement.executeQuery();
while (resultSet.next()) {
String name= resultSet.getString("stu_name");
String nickname= resultSet.getString("stu_nickname");
System.out.println(name +"-------"+nickname);
}
//8.回收资源
resultSet.close();
preparedStatement.close();
connection.close();
}

浙公网安备 33010602011771号