☕ 第十一章 JDBC
📄 一句话概括

JDBC(Java DataBase Connectivity)= Java 官方定的一套操作数据库的接口规范——Sun 定「总合同」,各数据库厂商照合同写「驱动」,Java 程序只面向接口写代码,换数据库几乎不用换代码。

数据库是谁:先认识一下新对手

前面十章的数据都存在文件里(IO 那座山翻完了)。但文件存数据有硬伤:查一条要遍历、多线程一起写容易乱、找"年龄 18 的波仔"得自己写循环。

真正干活的程序都把数据放数据库(如 MySQL)——专门的存数据软件,查询快、管得好、还认一门叫 SQL 的通用语言(SELECT * FROM student 这种)。

问题来了:Java 程序怎么跟数据库说话?MySQL 有 MySQL 的门卫规矩,Oracle 有 Oracle 的——要是每家的说法都不一样,你换一次数据库代码就得全部重写。

JDBC:Sun 出面定的总合同

Sun(Java 的爹)想了个办法——我定接口,你们实现:

Java 程序(只管调接口)
        │
   JDBC 接口(java.sql 包,Sun 定的合同)
        │
 ┌──────┼──────────┐
MySQL 驱动  Oracle 驱动  SQLServer 驱动   ← 厂商写的实现类,装在 jar 包里
        │
各家数据库

这套东西就叫 JDBC。仔细看,这就是 4.3 接口思想的最大实战:

换数据库 = 换一个驱动 jar + 改一下连接地址,业务代码一行不动。没有这份合同,Java 生态不可能统一数据库操作。

四大件:合同里的四个主要角色

角色 类型 职责 大白话
DriverManager 类 管理驱动、发放连接 叫车平台调度员
Connection 接口 代表一条到数据库的连接 接通的电话线
Statement 接口 把 SQL 送给数据库执行 传话筒
ResultSet 接口 装查询结果,逐行取数据 送来的快递箱

五步套路:每一段 JDBC 代码都是这个骨架

  1. 导入驱动 jar:把 mysql-connector-j-x.x.x.jar 复制进项目,IDEA 里右键 → Add as Library(不导入 = 光有合同没有实现,跑了白跑)
  2. 注册驱动:Class.forName("com.mysql.cj.jdbc.Driver");——眼熟吗?9.1 反射三把钥匙的第一把!按类名把驱动类加载进 JVM(新驱动会自动注册,但这行代码的原理必须懂)
  3. 获取连接:Connection conn = DriverManager.getConnection(url, user, password);——url 长这样:jdbc:mysql://localhost:3306/库名,相当于"拨号地址 + 账号密码"
  4. 定义 SQL,用 Statement 执行:增删改用 executeUpdate(sql) 返回行数;查询用 executeQuery(sql) 返回 ResultSet
  5. 处理结果,释放资源:结果集逐行 next() 取,最后 close——电话线、传话筒、快递箱都要还(try-with-resources 一手包办,10.2 的姿势)

全流程操作的是别人的服务器,随时可能出岔子(连不上、SQL 写错),所以 SQLException 是受检异常——5.2 的账,编译器逼你处理。

现在能做到哪一步

这节是概念节,先把"合同"看懂。真连上 MySQL 还差两样:装好 MySQL 数据库 + 下载驱动 jar——下一节(快速入门/获取连接)就会手把手把五步套路跑通,到时候保姆级带你装。

💡 30 秒实验:看看合同长什么样

在 IDEA 里随便写个类,敲 Connection 让 IDEA 自动导包,按住 Ctrl 点进去——你会发现全是 public interface 开头的空方法(只有签名没有方法体)。这就是"合同":JDK 只带了接口,不带任何实现,实现全在驱动 jar 里。

💡 30 秒实验二:看看 jar 包里是什么

找到一个 .jar 文件,右键 → 用压缩软件打开(7-Zip 就行)——里面是一堆 .class 文件和 META-INF 配置。jar 包 = class 文件的压缩包,没有神秘感。

常见误区

  1. 「JDBC 是个框架,要下载安装」——不是框架,是 JDK 自带的接口规范(java.sql 包),你不用装它;要下载的是各厂商的驱动 jar。
  2. 「导入了 JDBC 就能连数据库」——只导接口不导驱动 jar,等于拿着合同找不着干活的人。驱动才是实现。
  3. 「jar 复制进项目就算导入」——还得 Add as Library(让 IDEA 认识它),否则写代码时 Connection 都点不出来。这是新手第一大卡点,下节保姆级演示。
  4. 「换了数据库就要重写所有代码」——恰恰相反,这正是 JDBC 的卖点:换驱动 jar + 改 url,五步骨架原样复用(前提是 SQL 语句通用)。
  5. 「Class.forName(驱动类名) 是 JDBC 特有的咒语」——它是反射(9.1 的 Class.forName,按类名字符串加载类),只是恰好被 JDBC 用来完成驱动注册。三把钥匙第一次真刀真枪上岗。

自测一下

❓ Q1:JDBC 是接口还是实现?驱动 jar 里装的是什么?

JDBC 是 Sun 定的接口规范(java.sql 包里全是 interface);驱动 jar 里装的是厂商照合同写的实现类(.class 文件的压缩包)。

❓ Q2:为什么 Sun 只定接口不写实现?

数据库厂商各不相同,Sun 不知道也不该知道各家怎么连——只定合同(方法签名),实现交给懂自己数据库的厂商。这样 Java 程序面向接口编程,换数据库不动代码(4.3 + 4.4 多态思想)。

❓ Q3:五步套路是什么?哪一步用到了反射?

①导驱动 jar ②注册驱动 Class.forName ③getConnection 获取连接 ④Statement 执行 SQL ⑤处理结果释放资源。第②步是反射——按类名字符串加载驱动类(9.1 三把钥匙上岗)。

❓ Q4:executeUpdate 和 executeQuery 有什么区别?

executeUpdate 干增删改,返回受影响的行数(int);executeQuery 干查询,返回 ResultSet 结果集。一个"改动世界",一个"看一眼世界"。

❓ Q5(毕业题):为什么 JDBC 的 SQLException 是受检异常,而反射的 NoSuchMethodException 系列不是?用 5.2 的标准分析。

5.2 的标准:怪外部环境的受检,怪自己的是运行时。数据库连接依赖外部服务器(在别的机器上跑着、网线、账号密码),Java 代码再对也可能连不上——编译器必须逼你处理;反射方法名写错是你自己代码的问题,编译期本可避免,归运行时异常。

下一步学什么

相关笔记