JDBC
通过java代码操作数据库
流程:
加载驱动 -> 与数据库建立连接 -> 创建Statement() -> 执行sql语言 -> 处理返回结果
图1
封装数据库连接部分
封装的目的,可以反复使用
/*
* 封装jdbc工具类
*
* 1.创建连接
* 2.释放资源 略
*/
public class JdbcUtils {
private static final String DRIVER = "com.mysql.jdbc.Driver";
private static final String URL = "jdbc:mysql:///test";
private static final String USER = "root";
private static final String PASSWORD = "123456";
public static Connection getConnection(){
Connection conn = null;
try {
Class.forName(DRIVER);
conn = DriverManager.getConnection(URL,USER,PASSWORD);
} catch (SQLException e) {
e.printStackTrace();
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
return conn;
}
}
Statement
可以用来执行sql语句,execute操作时,不能动态修改字符串
stmt = conn.createStatement();
String sql = "insert into person values(null,'张三','男',21,'山东')";
int n = stmt.executeUpdate(sql);
prepareStatement
可以动态修改字符串,通过set+类型 可以动态设置sql的值。使用?作为占位符
Connection conn = JdbcUtils.getConnection();
String sql = "insert into person values(null,?,?,?,?)";
PreparedStatement pstmt = conn.prepareStatement(sql);
pstmt.setString(1, person.getName());
连接池
公共接口 javax.sql.DataSource
各个厂商实现该接口,即可使用
连接池的引入,使用阿里的druid
连接池特点:
- 用于存放多个连接的集合(加载驱动,创建连接被隐藏)
- 当用户需要操作数据库时,从连接池中直接申请
- java提供的公共接口 javax.sql.DataSource
public class JdbcUtils {
private static final String DRIVER = "com.mysql.jdbc.Driver";
private static final String URL = "jdbc:mysql:///test";
private static final String USER = "root";
private static final String PASSWORD = "123456";
//创建连接池
private static DruidDataSource dataSource = new DruidDataSource();
//给dataSource的属性赋值
static{
dataSource.setDriverClassName(DRIVER);
dataSource.setUrl(URL);
dataSource.setUsername(USER);
dataSource.setPassword(PASSWORD);
}
public static Connection getConnection(){
Connection conn = null;
try {
conn = dataSource.getConnection();
} catch (SQLException e) {
e.printStackTrace();
}
return conn;
}
}
BDUtils
操作数据库的工具,简化jdbc
可以对数据进行封装,读写方便
底层实现了数据库的数据 对 自定义类的赋值,所以可以直接用方法拿到对象
而不用逐个get/set
使用前:
while(rs.next()){
person = new Person();
person.setId(rs.getInt("id"));
person.setName(rs.getString("name"));
System.out.println(person);
}
使用后:
public List<Person> findAllPersons(){
List<Person> persons = null;
QueryRunner qr = new QueryRunner(JdbcUtils.getDataSource());
String sql = "select * from person";
try {
// 此处返回的为什么是集合?泛型方法,query可以根据结果集
// 返回不同的类型,可以有8种。模糊点
persons = qr.query(sql, new BeanListHandler<Person>(Person.class));
} catch (SQLException e) {
e.printStackTrace();
}
return persons;
}
事务
体现在数据的安全性,不同sql语句作为一个事务,要么都执行,要么都不执行
特别注意:使用连接池时,由于拿到的可能不是同一个连接,所以
在执行更新的时候,指定同一个连接Connection
Connection conn = null;
conn.setAutoCommit(false);
QueryRunner qr = new QueryRunner(dataSource);
qr.update(conn,sql1,params1);
conn.commit();
conn.rollback();
ACID
- 原子性 事务是不可分隔的单元,要么都执行成功,要么都执行失败
- 一致性 事务执行前后数据一致
- 隔离性 多个事务并发执行,互不干扰
- 持久性 事务一旦提交,会对数据库做永久修改