当前位置: 首页 > ops >正文

JDBC 的编写步骤及原理详解

一、JDBC 简介

JDBC(Java DataBase Connectivity)即 Java 数据库连接,是 Java 语言用于操作数据库的一套 API。它为多种关系数据库提供了统一的访问方式,允许 Java 程序与不同类型的数据库(如 MySQL、Oracle、SQL Server 等)进行连接和交互,实现对数据库的增删改查等操作。

二、JDBC 原理

(一)JDBC 架构

JDBC 采用了两层模型:

  • 应用程序层:即我们编写的 Java 程序,通过 JDBC API 来访问数据库。
  • 数据库驱动层:由数据库厂商提供的驱动程序,遵循 JDBC 规范,负责与具体的数据库进行通信。不同数据库有各自对应的驱动,如 MySQL 的驱动是com.mysql.cj.jdbc.Driver ,Oracle 也有其对应的驱动。

(二)核心接口和类

  1. DriverManager(驱动管理器)
    • 注册驱动:它的作用之一是让 JDBC 知道要使用哪个数据库驱动。例如,通过Class.forName("com.mysql.cj.jdbc.Driver") 加载 MySQL 驱动类,驱动类在加载时会自动将自己注册到DriverManager中。在早期也可以使用DriverManager.registerDriver(new com.mysql.cj.jdbc.Driver()) 来注册,但前者是更常用的方式。
    • 获取 Connection:负责获取与数据库的连接。当成功获取到Connection对象时,意味着 Java 程序与数据库建立了连接。它会根据传入的数据库 URL、用户名和密码等信息来尝试连接数据库。
  2. Connection(连接)
    • 代表 Java 程序与数据库之间的连接通道,与数据库的所有通讯都通过这个对象展开。
    • 最为重要的一个方法是用来获取Statement对象或PreparedStatement对象,通过这些对象来向数据库发送 SQL 语句。
  3. Statement(语句)
    • 用于向数据库发送 SQL 语句。可以执行不带参数的简单 SQL 语句,即静态 SQL 语句。例如,使用Statement执行查询语句:Statement st = conn.createStatement(); ResultSet rs = st.executeQuery("select * from table_name"); 。
    • 缺点是对于需要频繁执行且只有参数不同的 SQL 语句,性能较差,因为每次都要重新解析 SQL 语句。
  4. PreparedStatement(预编译语句)
    • Statement的子接口,它可以对 SQL 语句进行预编译,将 SQL 语句模板和参数分开。SQL 语句模板中使用占位符? 来代替实际参数。例如:String sql = "select * from user where name=?"; PreparedStatement ps = conn.prepareStatement(sql); ps.setString(1, "zhangsan"); 。
    • 优势在于提高了性能,因为预编译后的 SQL 语句在数据库端会被缓存,后续执行相同结构的 SQL 语句时,只需传入不同参数即可,无需重新解析 SQL;同时也增强了安全性,防止 SQL 注入攻击,因为参数是经过特殊处理后传入的。
  5. ResultSet(结果集)
    • 表示数据库执行查询操作后返回的结果集,是一个二维的表格形式,有行有列。
    • 提供了一系列方法来操作结果集,如boolean next() 方法用于将 “行光标” 移动到下一行,并返回移动后的行是否存在;XXX getXXX(int col) 方法用于获取当前行指定列上的值,列数从 1 开始计数 。

三、JDBC 编写步骤

(一)注册驱动

通过Class.forName("数据库驱动类名") 来加载数据库驱动类,使其自动注册到DriverManager中。例如,对于 MySQL 8.0 及以上版本,使用Class.forName("com.mysql.cj.jdbc.Driver") ;如果是 MySQL 5 及之前版本,则使用com.mysql.jdbc.Driver 。这一步告诉 Java 程序即将要连接的是哪个品牌的数据库。

(二)获取连接

使用DriverManager.getConnection(url, username, password) 方法获取与数据库的连接。其中:

  • url:是数据库的统一资源定位符,用于指定要连接的数据库位置和相关信息。格式由三部分组成,以 MySQL 为例,jdbc:mysql://IP地址:端口号/数据库名 ,如jdbc:mysql://localhost:3306/mydb ,表示连接本地 3306 端口上的名为mydb的数据库。还可以添加一些参数,如jdbc:mysql://localhost:3306/mydb?useUnicode=true&characterEncoding=UTF-8 ,用于指定字符集等。
  • username:登录数据库的用户名。
  • password:登录数据库的密码。

(三)获取数据库操作对象

根据不同需求获取StatementPreparedStatement对象:

  • 获取 Statement 对象:使用Connection对象的createStatement() 方法,如Statement stmt = conn.createStatement(); ,适用于执行简单的、不常变动的 SQL 语句。
  • 获取 PreparedStatement 对象:使用Connection对象的prepareStatement(String sql) 方法,传入 SQL 语句模板,如PreparedStatement pstmt = conn.prepareStatement("select * from user where id = ?"); ,适用于需要预编译、动态传入参数的场景。

(四)执行 SQL 语句

  1. 对于增删改操作:使用StatementexecuteUpdate(String sql) 方法或PreparedStatementexecuteUpdate() 方法(PreparedStatement因为已经预编译绑定了 SQL 语句,所以调用时不需要再传入 SQL 语句)。该方法返回一个整数,表示受影响的行数。例如:

java

String sql = "insert into user (name, age) values ('张三', 25)";
int affectedRows = stmt.executeUpdate(sql);

  1. 对于查询操作:使用StatementexecuteQuery(String sql) 方法或PreparedStatementexecuteQuery() 方法,返回一个ResultSet对象。例如:

java

String sql = "select * from user";
ResultSet rs = stmt.executeQuery(sql);

(五)处理查询结果(仅针对查询操作)

当执行查询操作得到ResultSet后,通过ResultSet的方法来遍历和获取数据。例如:

java

while (rs.next()) {int id = rs.getInt("id");String name = rs.getString("name");System.out.println("ID: " + id + ", Name: " + name);
}

这里通过next() 方法移动行光标,然后使用getIntgetString等方法根据列名或列索引获取对应的值。

(六)释放资源

使用完ConnectionStatement(或PreparedStatement )、ResultSet等资源后,要及时关闭,以释放数据库服务器资源和避免内存泄漏。一般在finally块中进行关闭操作,如下:

java

finally {if (rs != null) {try {rs.close();} catch (SQLException e) {e.printStackTrace();}}if (stmt != null) {try {stmt.close();} catch (SQLException e) {e.printStackTrace();}}if (conn != null) {try {conn.close();} catch (SQLException e) {e.printStackTrace();}}
}

以下是一个完整的 JDBC 操作 MySQL 数据库进行查询的示例代码:

java

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.Statement;public class JDBCExample {public static void main(String[] args) {Connection conn = null;Statement stmt = null;ResultSet rs = null;try {// 1. 注册驱动Class.forName("com.mysql.cj.jdbc.Driver");// 2. 获取连接String url = "jdbc:mysql://localhost:3306/mydb?useUnicode=true&characterEncoding=UTF-8";String username = "root";String password = "123456";conn = DriverManager.getConnection(url, username, password);// 3. 获取数据库操作对象stmt = conn.createStatement();// 4. 执行SQL语句String sql = "select * from user";rs = stmt.executeQuery(sql);// 5. 处理查询结果while (rs.next()) {int id = rs.getInt("id");String name = rs.getString("name");System.out.println("ID: " + id + ", Name: " + name);}} catch (Exception e) {e.printStackTrace();} finally {// 6. 释放资源if (rs != null) {try {rs.close();} catch (SQLException e) {e.printStackTrace();}}if (stmt != null) {try {stmt.close();} catch (SQLException e) {e.printStackTrace();}}if (conn != null) {try {conn.close();} catch (SQLException e) {e.printStackTrace();}}}}
}

通过网盘分享的文件:03_黑马程序员_JDBC_分析jdbc程序的编写步骤和原理.rar
链接: https://pan.baidu.com/s/1R0tf7XlurHOx-SlSq2ySFw 

http://www.xdnf.cn/news/6887.html

相关文章:

  • 素数筛(欧拉筛算法)
  • PIC16F18877 的主时钟 设置方法
  • Python爬虫实战:获取1688商品信息
  • [PMIC]PMIC重要知识点总结
  • 大数据会被AI取代?不!大数据才是AI的“智慧燃料”引擎
  • 烹饪实训室的行业标准实训
  • encrypt-labs AES 固定key
  • HelloWorld
  • 手写tomcat:基本功能实现(4)
  • webman用nginx代理静态json文件的异步跨域
  • 最小二乘法拟合平面(线性回归法、梯度下降、PCA法)
  • 2025年第三届盘古石杯初赛(智能冰箱,监控部分)
  • 深入理解 requestIdleCallback:浏览器空闲时段的性能优化利器
  • facebook开源分子化学数据集和模型(OMol25)论文速读
  • 典籍知识问答模块AI问答bug修改
  • 机器学习——逻辑回归
  • Mipsel固件Fuzzing小记
  • 计算机图形学编程(使用OpenGL和C++)(第2版)学习笔记 12.曲面细分
  • AUTOSAR图解==>AUTOSAR_SWS_HWTestManager
  • STM32H7时钟树
  • 开源语音-文本基础模型和全双工语音对话框架 Moshi 介绍
  • OTA与boot loader
  • 北大:基于因果的LLM形式化推理
  • 进阶-数据结构部分:3、常用查找算法
  • NVC++ 介绍与使用指南
  • 很啰嗦,再次总结 DOM
  • CAPL Class: TcpSocket (此类用于实现 TCP 网络通信 )
  • 使用教程:8x16模拟开关阵列可级联XY脚双向导通自动化接线
  • Vue-键盘事件
  • Elasticsearch Fetch阶段面试题