①ArrayHandler:把结果集中的第一行数据转成对象数组。
②ArrayListHandler:把结果集中的每一行数据都转成一个对象数组,再存放到List中。
③ BeanHandler :将结果集中的第一行数据封装到一个对应的JavaBean实例中。
④ BeanListHandler :将结果集中的每一行数据都封装到一个对应的JavaBean实例中,存放到List里。
⑤MapHandler:将结果集中的第一行数据封装到一个Map里,key是列名,value就是对应的值。
⑥MapListHandler:将结果集中的每一行数据都封装到一个Map里,然后再存放到List
⑦ColumnListHandler:将结果集中某一列的数据存放到List中。
⑧KeyedHandler(name):将结果集中的每一行数据都封装到一个Map里(List<Map>),再把这些map再存到一个map里,其key为指定的列。
⑨ScalarHandler:获取结果集中第一行数据指定列的值,常用来进行单值查询。
4、BeanHandler<T>
用于获取结果集中的第一行数据,并将其封装到JavaBean对象。
整个转换过程最终会在 BeanProcessor 类中完成。
执行代码:
1
2
3
4
5
6
7
|
//---- query 语句 ----
String sql =
"select * from users"
;
Users rs = runner.query(sql,
new
BeanHandler<Users>(Users.
class
));
// Print: BeanHandler: Users{id=1, userName='测试用户1', loginName='test1', userPassword='jiseflwes', userLevel=10, userLock=true}
System.out.println(
"BeanHandler: "
+ rs);
// Print: BeanHandler: test1
System.out.println(
"BeanHandler: "
+ rs.getLoginName());
|
需要注意的是,默认的情况下要保证表的字段和javabean的属性一致(字符一致即可,对大小写不敏感),比如字段是userLock,那么javabean中属性必须是userLock这几个字母(可以是userlock,userLock,userLOCK,不过还是建议按照规范来定义)。
但有个问题,数据表中的字段可能已经定下来了,而且名称可能不太规范,比如用下划线(login_name),或者加了一个类型前缀(chrLoginName),如果修改表字段,那么涉及到的修改地方太多了,其实查看源码可以知道BeanHandler有两个构造方法:
1
2
3
4
5
6
7
8
|
// BeanHandler 构造方法
public
BeanHandler(Class<T> type) {
this
(type, ArrayHandler.ROW_PROCESSOR);
}
public
BeanHandler(Class<T> type, RowProcessor convert) {
this
.type = type;
this
.convert = convert;
}
|
可以看出其实都是调用的第二个方法。
1
2
3
4
5
6
|
runner.query(sql,
new
BeanHandler<Users>(Users.
class
));
// 等价于
runner.query(sql,
new
BeanHandler<Users>(Users.
class
,
new
BasicRowProcessor()));
// 等价于
runner.query(sql,
new
BeanHandler<Users>(Users.
class
,
new
BasicRowProcessor(
new
BeanProcessor())));
// 所以关键的地方在 new BeanProcessor() 这个具体处理结果的对象
|
情况一:只涉及到下划线,表字段名用下划线间隔(如表users_t字段:[id],[user_name],[login_name],[user_password],[user_level],[user_lock]),现在要封装到Javabean中Users类(代码见上),其中属性使用驼峰命名。可以用dbutils1.6提供的BeanProcessor类的子类GenerousBeanProcessor。
1
2
3
4
5
6
7
8
9
10
|
String sql =
"select id,user_name,login_name,user_password,user_level,user_lock from users_t"
;
// 创建一个BeanProcessor对象
// GenerousBeanProcessor 仅仅重写了父类BeanProcessor的mapColumnsToProperties方法
BeanProcessor bean =
new
GenerousBeanProcessor();
// 将GenerousBeanProcessor对象传递给BasicRowProcessor
RowProcessor processor =
new
BasicRowProcessor(bean);
// 最后使用GenerousBeanProcessor的mapColumnsToProperties处理表字段到javabean的属性映射
Users rs = runner.query(sql,
new
BeanHandler<Users>(Users.
class
, processor));
// Print: BeanHandler: Users{id=1, userName='测试用户1', loginName='test1', userPassword='jiseflwes', userLevel=10, userLock=true}
System.out.println(
"BeanHandler: "
+ rs);
|
情况二:完全改变表字段到Javabean属性的映射(如表users_m字段:[yhmid],[charUsername],[charLoginName],[charPassword],[intLevel],[boolLock])映射到Users类(代码同上):
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
// BeanProcessor 有两个构造方法,可以传入一个HashMap集合
// HashMap 规定了表字段映射到Javabean的哪个属性,即key为字段名称,value为对应的javabean属性
// map.put(表字段名称, Javabean属性名称)
Map<String, String> map =
new
HashMap<String, String>();
map.put(
"yhmid"
,
"id"
);
map.put(
"charUsername"
,
"userName"
);
map.put(
"charLoginName"
,
"loginName"
);
map.put(
"charPassword"
,
"userPassword"
);
map.put(
"intLevel"
,
"userLevel"
);
map.put(
"boolLock"
,
"userLock"
);
// 用构建好的HashMap建立一个BeanProcessor对象
BeanProcessor bean =
new
BeanProcessor(map);
RowProcessor processor =
new
BasicRowProcessor(bean);
Users rs = runner.query(sql,
new
BeanHandler<Users>(Users.
class
, processor));
// Print: BeanHandler: Users{id=1, userName='测试用户1', loginName='test1', userPassword='jiseflwes', userLevel=10, userLock=true}
System.out.println(
"BeanHandler: "
+ rs);
|