MySQL-JDBC

本文介绍了JDBC(Java DataBase Connectivity),它是用Java语言连接数据库的技术,本质是操作数据库的规范。文中详细讲解了JDBC快速入门步骤,涉及的包和类,如DriverManager、Connection等,还介绍了数据库类型与Java类型对照、数据库工具类、表与类的关系,以及JDBC事务在MySQL和JDBC中的操作。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

JDBC概念

什么是JDBC:Java DataBase Connectivity 使用Java语言连接数据库的技术。

本质:是官方定义的操作数据库的一套规范,规则,都是接口。各个数据库厂商去实现这套接口,提供对应的数据库驱动jar包。我们可以使用这个驱动jar包,来完成连接数据库操作数据库的功能。

快速入门

步骤:

  1. 添加jar包到工程中,添加到工程的lib文件夹下,右键选择Bulib puth 中的Add…(eclipse中) (Add as Library(idea中))

  2. public class JDBCDemo {
    	
    	public static void main(String[] args) throws Exception {
    		//2注册驱动 com.mysql.jdbc.Driver.class
    		Class.forName("com.mysql.jdbc.Driver");// 通过该类的路径反射生成该类的字节码对象
    		//3.获取数据库的连接对象 Connection
    		Connection connection = DriverManager.getConnection("jdbc:mysql://localhost:3306/java31", "root", "root");
    		//4.准备sql语句
    		String sql = "update account set balance = 20000 where username = '张三'";
    		//5.获取执行sql语句的对象 Statement
    		Statement createStatement = connection.createStatement();
    		//6.通过Statement对象执行sql语句
    		int count = createStatement.executeUpdate(sql);
    		//如果>0就代表执行成功
    		if(count > 0) {
    			System.out.println("成功");
    		}else {
    			System.out.println("失败");	
    		}
    		//打开的连接对象关闭,先开后关,后开先关.
    		createStatement.close();
    		connection.close();
    	}
    }
    

介绍JDBC快速入门用到的包和类

  • java.sql 所有与JDBC访问数据库相关的类和接口。
  • javax.sql 用到数据库连接池 数据库的扩展包,提供数据库操作额外的功能,如:连接池。
类,接口
  • DrierManager 驱动管理 注册驱动,还有获取数据库连接对象(类)
  • Connection 连接对象,用于创建执行sql对象 Statement、PreparedStatement对象
  • Statement sql语句执行对象,用于将sql语句发送给数据库服务器
  • PreparedStatement sql语句执行对象,是Statement的子接口
  • ResultSet 用于封装从数据库查询出来的结果值
DrierManager类
  • 从JDBC3开始,可以不用注册驱动直接使用。Class.forName();可以省略

  • 驱动类路径 com.mysql.jdbc.Driver

  • Connection getConnection(url,user,password):可以获取到数据库的连接对象

  • Connection getConnection(url,Properties info):通过连接字符串和属性对象 获取数据连接对象

  • user :登录数据库用户名

  • password :登录数据库的密码

  • url:连接数据库的路径 对于mysql而言是:jdbc:mysql://服务器ip地址:端口号3306/数据库名称[?参数名 = 参数值]

  • jdbc:mysql://服务器ip地址:端口号3306/数据库名称[?参数名 = 参数值]; 如果数据库服务器是在本地中,可以省略掉ip地址和端口号–> jdbc:mysql:///数据库名称[?参数名 = 参数值]
    如果数据传输时引发类乱码,后面可以使用参数 charcaterEncoding=utf8–>
    jdbc:mysql:///数据库名称?charcaterEncoding=utf8

Connection接口

作用:连接数据库,它是一个接口,由具体的厂商来提供具体的实现类,代表的是一个连接对象

  • Statement createStatement() 创建一个sql执行对象
  • PrepareStatement preparedStatement() 创建一个sql预处理对象
Statement接口

作用:用来执行sql语句,本质是把sql语句发送给数据库服务器

  • int executeUpdate(sql) :用于把sql语句发送给服务器,执行增删改操作。返回值int 影响数据库的记录数(行数)
  • ResultSet executeQuery(String sql) :用于把sql语句发送给服务器,执行查询操作,返回值ResultSet 查询返回的结果集
PreparedStatement
  • 执行sq的l对象

  • 会防止一些sql非法注入问题,在拼接sql语句时,可能会造成安全性问题。如:

    " select * from account where username like '% " +username + " % ’ and balance = ’ " + balance + " ’ + " or 1 = 1 "

    此时出现 " or 1=1 " 非法拼接问题。

    使用预编译的sql,参数使用作为占位符

    操作:

    • 在sql语句中涉及到参数时使用替代具体的数据 如: select * from user where username = ? and password = ?

    • 使用连接对象执行sql语句获取预编译对象 connection.preparedStatement(String sql)

    • 给?赋值:

      ​ 使用方法:setXxx(索引下标,?对应的实际值)

    • 使用预编译对象执行sql,获取返回的结果集值—>preparedStatement.executeQuery();

    • 处理结果,释放资源。

释放资源
  • 需要释放的资源对象:ResultSet对象,Statement对象,Connection对象
  • 释放的顺序:先开后关,后开先关 ResultSet–>Statement–>Connection
  • 释放资源:使用finally语句块,一定会被加载到。不能单独使用,搭配try语句块。

常用数据库数据类型和Java类型对照

sqljdbc方法Java
intgetInt()int
bigIntgetLong()long
bitgetBoolean()boolean
varchargetString()String
date/time/TimeStampgetDate/getTime/getTimeStampjava.util.Date/java.sql.Time/java.sql.Timestamp

备注:java.sql.Date/Time/TimeStamp (时间戳) 三个共同的父类时–>java.util.Date

数据库工具类 DBUtil

// 数据库工具类
public class DBUtil {
	    // 定义四个常量值
		private static final String DRIVER = "com.mysql.jdbc.Driver";
		private static final String URL = "jdbc:mysql:///java31?characterEncoding=utf8";
		private static final String USER = "root";
		private static final String PASSWORD = "root";
		// 定义JDBC常用类和接口
		private static Connection con = null;
		private static Statement st = null;
		private static PreparedStatement ps = null;
		private static ResultSet set = null;
		
		static {
			try {
				Class.forName(DRIVER);
				con = DriverManager.getConnection(URL, USER, PASSWORD);
			} catch (Exception e) {
				e.printStackTrace();
			}
		}
		// 针对查询的功能
		public static ResultSet select(String sql,Object[] args) {
			//String sql2   =  "select * from account where u_name = ? and password = ?"; 
			try {
				// 获取预处理对象
				 ps = con.prepareStatement(sql);
				 // 使用sql语句中的占位符  ?
				 // 遍历数组
				 // 占位符 在sql中是有前后顺序的   u_name对应的问号 索引是 1 password对应的问号就是2
				 for (int i = 0; i < args.length; i++) {
					// 把问号提换成具体的数据
					ps.setObject(i+1, args[i]);
				}
			   // 执行sql语句 获取结果值
			   set = ps.executeQuery();
			} catch (SQLException e) {
				e.printStackTrace();
			}
			return set;
		}
		// 针对更新的功能  insert update delete  executeUpdate()
		public static int update(String sql,Object[] args) {
			// 获取预处理对象
			// 定义一个变量 用来记录印象数据库表的行数
			int count = 0;
			 try {
				ps = con.prepareStatement(sql);
				 // 使用sql语句中的占位符  ?
				 // 遍历数组
				 // 占位符 在sql中是有前后顺序的   u_name对应的问号 索引是 1 password对应的问号就是2
				 for (int i = 0; i < args.length; i++) {
					// 把问号提换成具体的数据
					ps.setObject(i+1, args[i]);
				}
			   // 执行sql语句 获取结果值
			   count = ps.executeUpdate();
			} catch (SQLException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			// 返回给调用处 
			return count;
		}	
		// 关闭连接的方法
		public static void closeAll() {
			// 关闭时 先关闭ResultSet
				if (set != null) {
					try {
						set.close();
					} catch (SQLException e) {
						e.printStackTrace();
					}
				}
				if (st != null) {
					try {
						st.close();
					} catch (SQLException e) {
						e.printStackTrace();
					}
				}
				if (con != null) {
					try {
						con.close();
					} catch (SQLException e) {
						e.printStackTrace();
					}
				}
		}
}
表与类的关系
  • 整个表可以看做成一个类

  • 表的每一行称之为一条记录,可以看做成一个类的实例

  • 表中的每一列可以看做成实例对象中的每个属性。

  • 实体类、model类需要和数据库中的类进行一一映射

    • 表中的列名和model类中的属性名保持一致
    • 表中的列字段数据类型和model类中的属性数据类型保持一致

JDBC事务

事务:一个包含多个步骤或业务操作。如果这个业务或者多个步骤被事务管理,则这多个步骤,要么同时成功,要么回滚(多个步骤同时执行失败),这多个步骤是一个整体,不可分割的

操作:
mysql中
  • 开启事务:start transaction
  • 提交事务:commit
  • 回滚事务:rollback
JDBC中,

需要使用Connection对象来管理事务

  • 开启事务:setAutoCommit(boolean autoCommit); :执行该方法里面传入false值,手动开启事务 --> 在所有sql语句执行之前开启事务
  • 提交事务:commit();方法 -->当所有的sql语句执行完毕才提交事务
  • 回滚事务:rollback();方法 -->当事务中发生异常时回滚事务,回滚事务放在catch语句中

实例:以银行转账为例,让张三给李四转账10000

public class TransformTest {

    private static PreparedStatement ps1 = null;
    private static PreparedStatement ps2 = null;

    public static void main(String[] args) {
        //transform01();
        transform02();
    }
    //含有事务的方法
    public static void transform02(){
        //让张三的钱减少10000
        //让李四的钱增减10000
        //定义实现转账的两条sql语句
        double money = 10000;
        String username01 = "张三";
        String username02 = "李四";
        String sql1 = "update account set balance = balance - ? where username = ?";
        String sql2 = "update account set balance = balance + ? where username = ?";

        //使用Connection对象手动开启事务 set
        Connection connection = DBUtil.getConnection();
        try {
            connection.setAutoCommit(false);
            //先让张三的钱-10000
            //通过connection获取预处理对象
            ps1 = connection.prepareStatement(sql1);
            ps1.setDouble(1,money);
            ps1.setString(2,username01);
            //执行sql语句
            int count1 = ps1.executeUpdate();

            //制造一个异常
            int i = 1 / 0;

            //先让张三的钱-10000
            //通过connection获取预处理对象
            ps2 = connection.prepareStatement(sql2);
            ps2.setDouble(1,money);
            ps2.setString(2,username02);
            //执行sql语句
            int count2 = ps2.executeUpdate();
            //提交事务
            connection.commit();
            System.out.println("转账成功");
        } catch (Exception e) {
            System.out.println("转账失败");
            //回滚事务
            try {
                connection.rollback();
            } catch (SQLException throwables) {
                throwables.printStackTrace();
            }
            e.printStackTrace();
        }finally {
            //把打开的连接对象释放掉
            try {
                ps1.close();
                ps2.close();
                connection.close();
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
    }

    //不带事务的转账
    public static void transform01(){
        //让张三的钱减少10000
        //让李四的钱增减10000
        //定义实现转账的两条sql语句
        double money = 10000;
        String username01 = "张三";
        String username02 = "李四";
        String sql1 = "update account set balance = balance - ? where username = ?";
        String sql2 = "update account set balance = balance + ? where username = ?";

        //张三减少10000
        int count01 = DBUtil.update(sql1, new Object[]{money, username01});

        //制造一个程序异常
        int i = 1/0;

        //李四增加10000
        int count02 = DBUtil.update(sql2, new Object[]{money, username02});
        if (count01 > 0 && count02 > 0){
            System.out.println("转账成功");
        }else {
            System.out.println("转账失败");
        }
        //释放资源
        DBUtil.closeAll();
    }
}

。。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值