commons-dbutils 是 Apache 组织提供的一个开源 JDBC工具类库,它是对JDBC的简单封装,学习成本极低,并且使用dbutils能极大简化jdbc编码的工作量,创建连接、结果集封装、释放资源,同时也不会影响程序的性能。创建连接、结果集封装、释放资源因此dbutils成为很多不喜欢hibernate的公司的首选。
API介绍:
org.apache.commons.dbutils.QueryRunner — 核心类。执行SQL查询以处理结果集。这个类是线程安全的。
org.apache.commons.dbutils.ResultSetHandler — 结果集封装器
org.apache.commons.dbutils.DbUtils — 工具类
学习地址及jar包下载:http://commons.apache.org/proper/commons-dbutils/download_dbutils.cgi
连接数据库jar包mysql-connector-java-5.1.47:https://dev.mysql.com/downloads/connector/j/
本文是使用的数据库连接池是上一篇使用的C3P0文章链接:https://blog.csdn.net/SYJ_1835_NGE/article/details/88694434
DbUtils:提供如加载驱动、关闭连接、事务提交、回滚等常规工作的工具类,里面的所有方法都是静态的。主要方法如下:
DbUtils类提供了三个重载的关闭方法close() 。这些方法检查所提供的参数是不是NULL,如果不是的话,它们就关闭Connection、Statement和ResultSet。
public static void close(Connection conn) throws SQLException
public static void close(ResultSet rs) throws SQLException
public static void close(Statement stmt) throws SQLException
这一类"quietly"方法不仅能在Connection、Statement和ResultSet为NULL情况下避免关闭,还能隐藏一些在程序中抛出的SQLException。
public static void closeQuietly(Connection conn,Statement stmt, ResultSet rs)
public static void closeQuietly(Connection conn)
public static void closeQuietly(ResultSet rs)
public static void closeQuietly(Statement stmt)
用来提交连接,然后关闭连接,并且在关闭连接时不抛出SQL异常。
static void commitAndClose(Connection conn)
static void commitAndCloseQuietly(Connection conn)
装载并注册JDBC驱动程序,如果成功就返回true。使用该方法,你不需要捕捉这个异常ClassNotFoundException。
static boolean loadDriver(ClassLoader classLoader, String driverClassName)
static boolean loadDriver(String driverClassName)
用于事务的回滚并且在资源使用完后将连接关闭
static void rollback(Connection conn)
static void rollbackAndClose(Connection conn)
static void rollbackAndCloseQuietly(Connection conn)
注意:
1、如果使用 QueryRunner(DataSource ds) 构造器创建QueryRunner对象,需要使用连接池,如DBCP、C3P0等等,数据库事务交给DBUtils框架进行管理 ---- 默认情况下每条SQL语句单独一个事务。
2、如果使用 QueryRunner() 构造器创建QueryRunner对象 ,需要自己管理事务,因为框架没有连接池无法获得数据库连接。
该类简单化了SQL查询,它与ResultSetHandler组合在一起使用可以完成大部分的数据库操作,能够大大减少编码量。
QueryRunner类提供了两个比较常使用的构造方法:
默认的构造方法(无参的构造函数):在执行查询操作的时候需要手动传入Connection对象
public QueryRunner()
需要一个 javax.sql.DataSource 来作参数的构造方法:
public QueryRunner(DataSource ds)
使用数据库连接池来获取数据源,C3P0、DBCP或者Durid
public static DataSource getDataSource() {
return ds;
}
常用方法:
批处理
batch(Connection conn, String sql, Object[][] params) // 传递连接批处理
batch(String sql, Object[][] params) // 不传递连接批处理
更新操作
//无参构造函数需要手动传入连接对象
int update(Connection conn, String sql)
int update(Connection conn, String sql, Object... params)
int update(Connection conn, String sql, Object param)
//有参的构造函数(传入数据源的)Object... params和参数注入的 ?一 一对应
int update(String sql)
int update(String sql, Object... params)
int update(String sql, Object param)
查询操作
T query(Connection conn, String sql, ResultSetHandler rsh)
T query(Connection conn, String sql, ResultSetHandler rsh, Object... params)
T query(String sql, ResultSetHandler rsh)
T query(String sql, ResultSetHandler rsh, Object... params)
该接口用于处理 java.sql.ResultSet,将数据库的记录按要求转换为另一种形式。(List、Map、Bean等)
ResultSetHandler 接口提供了一个单独的方法:
//将参数中的结果集ResultSet rs转化为另外一种形式
T handle(ResultSet rs) throws SQLException
ResultSetHandler 接口的实现类(构造方法不唯一,在这里只用最常见的构造方法):
**BeanHandler(Class extends T> type):**将结果集中的第一行数据封装到一个对应的JavaBean实例中。也可以指定参数返回指定参数所在行的数据,下面有例子进行展示
**BeanListHandler(Class type):**将结果集中的每一行数据都封装到一个对应的JavaBean实例中,存放到List里。
**ArrayHandler():**把结果集中的第一行数据转成对象数组(存入Object[])。
**ArrayListHandler():**把结果集中的每一行数据都转成一个对象数组,再存放到List中
**ScalarHandler(int columnIndex) || ScalarHandler(String columnIndex):**通常用来保存只有一行一列的结果集。通常用来执行聚合函数
**MapHandler():**将结果集中的第一行数据封装到一个Map里,key是列名,value就是对应的值。
**MapListHandler():**将结果集中的每一行数据都封装到一个Map里,然后再将所有的Map存放到List中。
**BeanMapHandler(Class
BeanMapHandler(Class<V> type)
BeanMapHandler(Class<V> type, int columnIndex)
BeanMapHandler(Class<V> type, RowProcessor convert)
BeanMapHandler(Class<V> type, String columnName)
**KeyedHandler(String columnName):**将结果集每一行数据保存到一个“小”map中,key为列名,value该列的值,再将所有“小”map对象保存到一个“大”map中 , “大”map中的key为指定列,value为“小”map对象
KeyedHandler(
KeyedHandler(int columnIndex)
KeyedHandler(RowProcessor convert)
KeyedHandler(String columnName)
创建mydb数据库和employee表
CREATE TABLE `employee` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`username` varchar(20) DEFAULT NULL,
`salary` int(12) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=14 DEFAULT CHARSET=utf8
---------------------
作者:SYJ_追梦逐星
来源:CSDN
原文:https://blog.csdn.net/SYJ_1835_NGE/article/details/88694434
版权声明:本文为博主原创文章,转载请附上博文链接!
导入相关jar包 commons-dbutils-1.7.jar
创建QueryRunner对象。依赖于数据源DataSource
//数据源可以通过C3P0、DBCP或者Druid获取
QueryRunner queryRunner = new QueryRunner(C3P0Utils.getDataSource());
调用QueryRunner的方法来完成CRUD的操作
对于CUD,执行DML语句。增、删、改语句。
public class Demo1 {
//如果使用 QueryRunner(DataSource ds) 构造器创建QueryRunner对象,需要使用连接池,
// 如DBCP、C3P0等等,数据库事务交给DBUtils框架进行管理 ---- 默认情况下每条SQL语句单独一个事务。
//如果使用 QueryRunner() 构造器创建QueryRunner对象 ,需要自己管理事务,因为框架没有连接池无法获得数据库连接。
@Test
//快速感受DBUtils之插入操作
public void test1() {
String sql = "insert into employee (username,salary) values (?,?)";
QueryRunner queryRunner = new QueryRunner(C3P0Utils.getDataSource());
try {
int count = queryRunner.update(sql, "蜘蛛精", "1000");
if (count > 0) {
System.out.println("插入成功");
} else {
System.out.println("插入失败");
}
} catch (SQLException e) {
e.printStackTrace();
}
}
@Test
//快速感受DBUtils之更新操作
public void test2() {
String sql = "update employee set username=? where id=?";
QueryRunner queryRunner = new QueryRunner(C3P0Utils.getDataSource());
try {
int count = queryRunner.update(sql, "蛇精", 12);
if (count > 0) {
System.out.println("更新成功");
} else {
System.out.println("更新失败");
}
} catch (SQLException e) {
e.printStackTrace();
}
}
@Test
//快速感受DBUtils之删除操作
public void test3() {
String sql = "delete from employee where username=?";
QueryRunner queryRunner = new QueryRunner(C3P0Utils.getDataSource());
try {
int count = queryRunner.update(sql, "蛇精");
if (count > 0) {
System.out.println("刪除成功");
} else {
System.out.println("刪除失败");
}
} catch (SQLException e) {
e.printStackTrace();
}
}
// 对于R,需要用到ResultSetHandler接口,该接口有9大实现类
}
执行查询语句,将其封装成不同的数据方式。
public interface employeeDao {
/**
實現DBUtils的CRUD
包含九种不同类型的查询结果的封装
*/
//CUD操作
public void add()throws SQLException;
public void update()throws SQLException;
public void delete()throws SQLException;
//简单的查询操作
//对结果集的封装
public employee findById(int id)throws SQLException;
public List<employee> findAll()throws SQLException;
public Long findCount()throws SQLException;
public String findArrayHandler()throws SQLException;
public List<Object[]> findArrayListHandler()throws SQLException;
public Map<Integer, employee> findBeanMapHandler()throws SQLException;
public Map<Object, Map<String, Object>> findKeyedHandler(int id )throws SQLException;
public Map<String, Object> findMapHandler()throws SQLException;
public List<Map<String, Object>> findMapListHandler()throws SQLException;
}
public class employeeDaoImpl implements employeeDao {
QueryRunner runner = null;
public employeeDaoImpl() {
runner = new QueryRunner(C3P0Utils.getDataSource());
}
@Test
//添加一条employee
@Override
public void add() throws SQLException {
String sql = "insert into employee (username , salary) values (?,?) ";
int count = runner.update(sql, "太上老君", 12000);
if (count > 0) {
System.out.println("添加成功");
} else {
System.out.println("添加失败");
}
}
@Test
//更新employee
@Override
public void update() throws SQLException {
String sql = "update employee set username=? where id=?";
int count = runner.update(sql, "牛魔王", 11);
if (count > 0) {
System.out.println("更新成功");
} else {
System.out.println("更新失败");
}
}
@Test
//删除employee
@Override
public void delete() throws SQLException {
String sql = "delete from employee where username=?";
int count = runner.update(sql, "牛魔王");
if (count > 0) {
System.out.println("刪除成功");
} else {
System.out.println("刪除失败");
}
}
/**
* BeanHandler
* BeanListHandler
* ScalarHandler
* ArrayHandler
* ArrayListHandler
* MapHandler
* MapListHandler
* BeanMapHandler
* KeyedHandler
*/
// BeanHandler 过id查找employee(结果集BeanHandler)
@Override
public employee findById(int id) throws SQLException {
String sql = "select * from employee where id =?";
employee e = runner.query(sql, new BeanHandler<employee>(employee.class), id);
System.out.println(e);
return e;
}
// BeanListHandler 查找所有employee(结果集BeanListHandler)
@Override
public List<employee> findAll() throws SQLException {
String sql = "select * from employee ";
List<employee> list = runner.query(sql, new BeanListHandler<employee>(employee.class));
return list;
}
// ScalarHandler 查找employee的总数(结果集ScalarHandler)
@Override
public Long findCount() throws SQLException {
String sql = "select count(id) from employee ";
Long count = runner.query(sql, new ScalarHandler<Long>());
return count;
}
@Override
// ArrayHandler 将结果集第一行数据保存到Object[]中(结果集ArrayHandler)
public String findArrayHandler() throws SQLException {
String sql = "select * from employee";
Object[] obj = runner.query(sql, new ArrayHandler());
return Arrays.toString(obj);
}
@Override
// ArrayListHandler 将结果集每一条数据,转为Object[],再保存到list集合中(结果集ArrayListHandler)
public List<Object[]> findArrayListHandler() throws SQLException {
String sql = "select * from employee";
List<Object[]> list = runner.query(sql, new ArrayListHandler());
return list;
}
@Override
// BeanMapHandler 将结果集每一条数据,转为JavaBean对象,再保存到map集合中(结果集BeanMapHandler)
public Map<Integer, employee> findBeanMapHandler() throws SQLException {
String sql = "select * from employee";
Map<Integer, employee> map = runner.query(sql, new BeanMapHandler<>(employee.class));
return map;
}
@Override
// KeyedHandler 将结果集每一行数据保存到一个“小”map中,key为列名,value该列的值,再将所有“小”map对象保存到一个“大”map中
// “大”map中的key为指定列,value为“小”map对象(结果集KeyedHandler)
public Map<Object, Map<String, Object>> findKeyedHandler(int id) throws SQLException {
String sql = "select * from employee";
Map<Object, Map<String, Object>> maps = runner.query(sql, new KeyedHandler<>(id));
return maps;
}
@Override
// MapHandler 将结果集第一行数据封装到Map集合中,key是列名,value为该列的值(结果集MapHandler)
public Map<String, Object> findMapHandler() throws SQLException {
String sql = "select * from employee";
Map<String, Object> map = runner.query(sql, new MapHandler());
return map;
}
@Override
// MapListHandler 将结果集每一行数据保存到map中,key列名 value该列的值 ---- 再将所有map对象保存到List集合中
//(结果集MapListHandler)
public List<Map<String, Object>> findMapListHandler() throws SQLException {
String sql = "select * from employee";
List<Map<String, Object>> lists = runner.query(sql, new MapListHandler());
return lists;
}
}
public class Mian {
public static void main(String[] args) throws SQLException {
employeeDaoImpl emi = new employeeDaoImpl();
//BeanHandler类
// emi.findById(1);
//BeanListHandler类
//List list = emi.findAll();
//System.out.println(list);
//ScalarHandler类
//Long count = emi.findCount();
//System.out.println(count);
//ArrayHandler类
//String str = emi.findArrayHandler();
//System.out.println(str);
//ArrayListHandler类
//List
导入相应jar包。
创建JdbcTemplate对象。依赖于数据源DataSource
Druid的相关介绍:https://blog.csdn.net/SYJ_1835_NGE/article/details/88694434
//DruidUtils是Druid数据库连接池抽取的工具类
//传入数据源
JdbcTemplate template = new JdbcTemplate(DruidUtils.getDataSource());
调用JdbcTemplate的方法来完成CRUD的操作
update():执行DML语句。增、删、改语句
queryForMap():查询结果将结果集封装为map集合,将列名作为key,将值作为value 将这条记录封装为一个map集合
queryForList():查询结果将结果集封装为list集合
query():查询结果,将结果封装为JavaBean对象
query的参数:RowMapper
一般我们使用BeanPropertyRowMapper实现类。可以完成数据到JavaBean的自动封装
new BeanPropertyRowMapper<类型>(类型.class)
List<User> list= template.query(sql, new BeanPropertyRowMapper<User>(User.class));
queryForObject:查询结果,将结果封装为对象
创建一个mydb数据库和一个user表:
user | CREATE TABLE `user` (
`id` int(10) NOT NULL AUTO_INCREMENT,
`username` varchar(255) DEFAULT NULL,
`password` varchar(20) DEFAULT NULL,
`score` double(4,2) DEFAULT NULL,
`address` varchar(255) DEFAULT NULL,
`brith` date DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=9 DEFAULT CHARSET=utf8
编写User实体类
public class User {
Integer id;
String username;
String password;
Double score;
String address;
Date brith;
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public Double getScore() {
return score;
}
public void setScore(Double score) {
this.score = score;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public Date getBrith() {
return brith;
}
public void setBrith(Date brith) {
this.brith = brith;
}
@Override
public String toString() {
return "User{" +
"id=" + id +
", username='" + username + '\'' +
", password='" + password + '\'' +
", score=" + score +
", address='" + address + '\'' +
", brith=" + brith +
'}';
}
}
执行增删改操作
public class Test1 {
private JdbcTemplate template = new JdbcTemplate(DruidUtils.getDataSource());
//1、修改id为1的score为10000
@Test
public void test1() {
String sql = "update user set score=? where id=?";
int count = template.update(sql, 88.88, 1);
if (count > 0) {
System.out.println("更新数据成功!!!");
} else {
System.out.println("更新数据失败!!!");
}
}
//2、添加一条记录
@Test
public void test2() {
String sql = "insert into user values (?,?,?,?,?,?)";
int count = template.update(sql, null, "孙悟空", "222222", "63.36", "广东", "1996-06-11");
if (count > 0) {
System.out.println("插入数据成功!!!");
} else {
System.out.println("插入数据失败!!!");
}
}
//3、删除一条记录
@Test
public void test3() {
String sql = "delete from user where id=?";
int count = template.update(sql, 8);
if (count > 0) {
System.out.println("删除数据成功!!!");
} else {
System.out.println("删除数据失败!!!");
}
}
}
执行查询语句
/**
* Spring JdbcTempalte的练习
*/
public class Test1 {
private JdbcTemplate template = new JdbcTemplate(DruidUtils.getDataSource());
//4、查询数据库为一将其封装成Map集合
@Test
public void test4() {
String sql = "select * from user where id=?";
Map<String, Object> map = template.queryForMap(sql, 1);
System.out.println(map);
}
//5、查询数据库所有记录将其封装成List
@Test
public void test5() {
String sql = "select * from user ";
List<Map<String, Object>> list = template.queryForList(sql);
for (Map<String, Object> map : list) {
System.out.println(map);
}
}
//6.1、查询数据库所有记录将其封装成指定的对象
@Test
public void test6() {
String sql = "select * from user ";
List<User> list= template.query(sql, new RowMapper<User>() {
@Override
public User mapRow(ResultSet rs, int i) throws SQLException {
User user = new User();
int id = rs.getInt("id");
String username = rs.getString("username");
String password = rs.getString("password");
double score = rs.getDouble("score");
String address = rs.getString("address");
Date brith = rs.getDate("brith");
user.setId(id);
user.setUsername(username);
user.setPassword(password);
user.setScore(score);
user.setAddress(address);
user.setBrith(brith);
return user;
}
});
for (User user : list) {
System.out.println(user);
}
}
//6.2、查询数据库所有记录将其封装成指定的对象
@Test
public void test6_1() {
String sql = "select * from user ";
// 星标重点
List<User> list= template.query(sql, new BeanPropertyRowMapper<User>(User.class));
for (User user : list) {
System.out.println(user);
}
}
//7、查询数据库所有记录的数量
@Test
public void test7() {
String sql = "select count(id) from user ";
Long counts = template.queryForObject(sql, Long.class);
System.out.println(counts);
}
}