1. JDBC的概念
Java代码实现的数据库连接技术,软件层面的(非可视化)客户端,从操作数据库的角度来看和navicat(可视化)没有太大区别,后者对数据库的操作,jdbc也可以,都属于客户端。
2. 有了navicat为什么还要用jdbc操作数据库?
navicat只是单纯地连接、操作数据库,无法书写后台代码和逻辑代码,无法定制化用户数据。
在实际开发过程中,如果要存储用户在浏览器页面输入提交的信息,如账号密码等,navicat不能对接浏览器,无法获取用户输入的信息,只有Java后台代码可以对接浏览器页面,获取用户输入提交的信息。
3. JDBC操作数据库的步骤
在idea中新建项目后,右键项目名字,新建文件夹 lib,把 mysql-connector-java jar包粘贴到 lib文件夹中,右键jar包 选择 Add as Library(汉化后是添加为库),能展开就能用了。
注:不同的数据库厂商根据JDBC提供的接口API规范,编写实现类 ,封装起来就是jar包,导入idea直接用
JDBC的原生代码分为六个步骤,实际开发中都是用的封装后的,在此简单了解即可,做到阅读无障碍。在书写原生代码的同时,打开数据库可视化工具navicat,方便观察执行结果
3.1 加载驱动
//一、强制触发类加载,加载驱动,括号内的参数是全限定名、路径
Class.forName("com.mysql.cj.jdbc.Driver");//会出现非运行时异常,此处直接上抛
3.2 建立数据库连接
/*二、建立数据库连接
jdbc:数据库类型://ip:port(端口号)/数据库名?
?左边是连接路径的正文,?右边是连接参数,编码集、字符集(utf-8防止乱码)、服务器时区,防止时间的使用出现偏差*/
String url = "jdbc:mysql://localhost:3306/day7.10" +
"?userUnicode=true&characterEncoding=utf-8&userSSL=false&serverTimezone=Asia/Shanghai";
Connection conn = DriverManager.getConnection(url,"root","200234");
3.3 创建发送sql的工具对象
3.3.1 增删改操作
//conn相当于navicat中的新建连接的那个“连接”,查询都是基于这个连接,
// 所以获取发送sql工具类的实现类对象要通过conn获取
//三、获取发送sql的工具
String sql = "insert into emp(ename,sal) values ('张1111111',6500)";
PreparedStatement ps = conn.prepareStatement(sql);
3.3.2 查询操作
//此处除了sql语句都一致
String sql = "select * from emp";
PreparedStatement ps = conn.prepareStatement(sql);
3.4 书写和发送执行sql语句
3.4.1 增删改操作
//四、发送执行sql
//增删改,返回的是被操作数据的行数,用整型接受
//查询返回的是ResultSet类型的集合
int n = ps.executeUpdate();
3.4.2 查询操作
//四、发送执行sql
//增删改,返回的是被操作数据的行数,用整型接受
//查询返回的是ResultSet类型的集合
ResultSet rs = ps.executeQuery(sql);
ResultSet的实现类对象rs,在调用get方法时候,根据字段类型决定:
- 整型字段:rs.getInt()、rs.getLong();
- 浮点字段:rs.getDouble();
- 字符字段:rs.getString();
- 日期字段:借助工具类Date
在获取字段时的两种传参方式:
通过序号 rs.getInt(1) rs.getString(2) 通过字段名 rs.getInt("user_id") rs.get("person_name") 注:推荐使用字段名,因为表中字段很多的话,还要一个一个数字段对应的序号,其次直接用字段名,更加清晰,便于阅读。
3.5 处理执行结果或结果集
3.5.1 增删改结果处理
//五、处理结果
if(n>0){
System.out.println("成功!");
}else{
System.out.println("失败!");
}
3.5.2 查询结果集合处理
//五、处理结果
//next()判断是否有下一个与元素,有的话指针后移
while(rs.next()){
//获取字段值,考虑到字段会为Null,则使用包装类型接收字段
Integer id = rs.getInt("eid");
String name = rs.getString("ename");
String sex = rs.getString("esex");
Date date = rs.getDate("hirdate");
Double sal = rs.getDouble("sal");
Integer deptId = rs.getInt("deptid");
System.out.println("id:"+id+" 姓名:"+name+" 性别:"+sex+" 入职时间:"+date+" 工资:"+sal+" 部门id:"+deptId);
}
3.6 关闭连接
//六、关闭资源
//从内往外关ps是通过conn获取的,如果先关闭conn的话,后期想用ps就不行了
ps.close();
conn.close();
如果是查询操作,在关闭ps前,添加rs的关闭语句:rs.close();
3.7 执行结果
3.7.1 增:
3.7.2 查:
4. 过程中对应的API
4.1 Driver
作用:告诉程序使用哪种数据库。
每个数据库驱动程序都必须实现的接口,当连接数据库的时候,可以通过触发强制类加载的方式,装载驱动:
Class.forName("com.mysql.cj.jdbc.Driver");
4.2 DriverManager
作用:管理驱动程序和建立数据库连接。
创建数据库连接:直接通过 类名. 调用静态方法 getConnection(url,user,password),传入数据库连接路径、用户名、密码,然后返回一个Connection类型的实例
4.3 Connection
作用:所有的SQL语句都是通过Connection实现类对象发送到数据库的。
- 创建Connection实例的过程相当于navicat中的新建连接的过程;
- 创建PreparedStatement实例的过程相当于navicat中新建查询的过程;
- 创建Connection实例conn后,调用prepareStatement(sql)或Statement(sql)方法,获取发送sql指令的工具
4.4 PreparedStatement
作用:执行预编译的sql语句,返回执行结果
- 增删改:返回整数
- 查询返回结果集 用 ResultSet 实例接收
Statement:不支持预编译,相同的sql语句会重复编译,性能相对低,同时不能处理SQL注入;
PreparedStatement:是 Statement 的子接口,继承了所有功能,并支持预编译,相同的sql语句执行多次时,只编译一次,提高性能;同时可以使用?作为占位符,执行sql语句前,用实际的参数值替换这些占位符,避免SQL注入的问题。
SQL注入:用户输入的字符串可能被插入到sql语句中,比如根据id查询:String id = sc.next(); //如果用户输入了 3 or 1=1,所有数据行都会展示出来 select * from emp where id = id;
4.5 ResultSet
执行Select查询操作时,会将数据库中的数据行(表中的行)封装成一个ResultSet对象,存储到集合中。
粗略理解:一个数据库表相当于一个类,一个数据行相当于一个对象,每个字段相当于属性。
标签:JDBC,rs,数据库,连接,初识,sql,id,conn From: https://blog.csdn.net/zyqq1314/article/details/140462306