本文已参与「新人创作礼」活动, 一起开启掘金创作之路。
在MP中,Wrapper接口的实现类关系如下:
可以看到,AbstractWrapper和AbstractChainWrapper是重点实现,接下来我们重点学习AbstractWrapper以及其子类。
AbstractWrapper是我们传统Java写法,
AbstractChainWrapper是Lambda表达式写法
说明:
QueryWrapper(LambdaQueryWrapper) 和 UpdateWrapper(LambdaUpdateWrapper) 的父类 用于生成 sql 的 where 条件, entity 属性也用于生成 sql 的 where 条件
注意: entity 生成的 where 条件与 使用各个 api 生成 的 where 条件没有任何关联行为
官网文档地址:baomidou.com/pages/10c80…
allEq(and操作匹配多个条件)
allEq(Map<R, V> params)
allEq(Map<R, V> params, boolean null2IsNull)
allEq(boolean condition, Map<R, V> params, boolean null2IsNull)
全部e(或个别isNull)
个别参数说明: params : key 为数据库字段名, value 为字段值 null2IsNull : 为 true 则在 map 的 value 为null 时调用 isNull 方法,为 false 时则忽略 value 为 null 的
例1: allEq({id:1,name:"老王",age:null}) ---> id = 1 and name = '老王' and age is null
例2: allEq({id:1,name:"老王",age:null}, false) ---> id = 1 and name = '老王'
allEq(BiPredicate<R, V> filter, Map<R, V> params)
allEq(BiPredicate<R, V> filter, Map<R, V> params, boolean null2IsNull)
allEq(boolean condition, BiPredicate<R, V> filter, Map<R, V> params, boolean
null2IsNull)
个别参数说明: filter : 过滤函数,是否允许字段传入比对条件中 params 与 null2IsNull : 同上
例1: allEq((k,v) -> k.indexOf("a") > 0, {id:1,name:"老王",age:null}) ---> name = '老王'
and age is null
例2: allEq((k,v) -> k.indexOf("a") > 0, {id:1,name:"老王",age:null}, false) ---> name =
'老王'
测试用例
用法1 直接查 如果字段为空会追加IsNull
/**
* Wrapper条件构造器- allEq
**/
@Test
public void allEq(){
Map<String,Object> map = new HashMap<>();
// 构造查询条件
map.put( "name" , "亚索" );
map.put( "age" , "10" );
map.put( "email" , "lol@qq.com" );
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
// 第一种用法 直接比较 and 拼接查询
queryWrapper.allEq(map);
List<User> userList = userMapper.selectList(queryWrapper);
for (User user : userList) {
System.out.println(user);
}
}
用法2 新增一个参数为false,默认为true,是否把空字段作为追加条件 如果字段为空不会追加IsNull.所以如果为false啧不会空字段作为查询条件
/** * Wrapper条件构造器- allEq **/ @Test public void allEq(){ Map < String,Object > map = new HashMap <> (); // 构造查询条件 map.put( "name" , "亚索" ); map.put( "age" , "10" ); map.put( "email" , "" ); QueryWrapper < User > queryWrapper = new QueryWrapper <> (); // 第一种用法 直接比较 and 拼接查询 // queryWrapper.allEq(map); // 第二种用法 如果字段为空不作为查询条件 queryWrapper.allEq(map, false ); List < User > userList = userMapper .selectList(queryWrapper); for ( User user : userList) { System. out .println( user ); } }
用法3 过滤 用的比较少 箭头函数对比参数,是否满足作为查询条件
/**
* Wrapper条件构造器- allEq
**/
@Test
public void allEq(){
Map<String,Object> map = new HashMap<>();
// 构造查询条件
map.put( "name" , "亚索" );
map.put( "age" , "10" );
map.put( "email" , "" );
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
// 第一种用法 直接比较 and 拼接查询
// queryWrapper.allEq(map);
// 第二种用法 如果字段为空不作为查询条件
// queryWrapper.allEq(map, false );
// 第三种用法 箭头函数对比参数,是否满足作为查询条件
// 如这个例子 三个参数只有age满足条件,所以只有age可以作为查询条件
queryWrapper.allEq((k,v)->(k.equals( "age" ) || k.equals( "id" )),map);
List<User> userList = userMapper.selectList(queryWrapper);
for (User user : userList) {
System.out.println(user);
}
}
基本比较操作
eq
等于 =
ne
不等于 <>
gt
大于 >
ge
大于等于 >=
lt
小于 <
le
小于等于 <=
between
BETWEEN 值1 AND 值2
notBetween
NOT BETWEEN 值1 AND 值2
in
字段 IN (value.get(0), value.get(1), ...)
notIn
字段 NOT IN (v0, v1, ...)
测试用例:
/**
* Wrapper条件构造器- eq
**/
@Test
public void Eq(){
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.eq( "password" , "123456" )
// ge是大于等于 >=
.ge( "age" ,20)
.in( "name" , "亚索" , "易" );
List<User> userList = userMapper.selectList(queryWrapper);
// SELECT id,user_name,password,name,age,email FROM tb_user WHERE password = '123456' AND age >= 20 AND name IN ( '亚索' , '易' )
for (User user : userList) {
System.out.println(user);
}
}
模糊查询
like
LIKE '%值%'
例: like("name", "王") ---> name like '%王%'
notLike
NOT LIKE '%值%'
例: notLike("name", "王") ---> name not like '%王%'
likeLeft
LIKE '%值'
例: likeLeft("name", "王") ---> name like '%王'
likeRight
LIKE '值%'
例: likeRight("name", "王") ---> name like '王%'
测试用例:
/**
* Wrapper条件构造器- like模糊查询
**/
@Test
public void Like(){
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.like( "user_name" , "剑" );
List<User> userList = userMapper.selectList(queryWrapper);
// SELECT id,user_name,password,name,age,email FROM tb_user WHERE user_name LIKE '%剑%'
for (User user : userList) {
System.out.println(user);
}
}
排序
orderBy
排序:ORDER BY 字段, ...
例: orderBy(true, true, "id", "name") ---> order by id ASC,name ASC
orderByAsc
排序:ORDER BY 字段, ... ASC
例: orderByAsc("id", "name") ---> order by id ASC,name ASC
orderByDesc
排序:ORDER BY 字段, ... DESC
例: orderByDesc("id", "name") ---> order by id DESC,name DESC
测试用例:
/**
* Wrapper条件构造器- orderBy排序
**/
@Test
public void orderBy(){
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
// 按照年龄倒序排序
queryWrapper.orderByDesc( "age" );
List<User> userList = userMapper.selectList(queryWrapper);
// SELECT id,user_name,password,name,age,email FROM tb_user ORDER BY age DESC
for (User user : userList) {
System.out.println(user);
}
}
逻辑查询
or
拼接 OR
主动调用 or 表示紧接着下一个方法不是用 and 连接!(不调用 or 则默认为使用 and 连接)
and
AND 嵌套
例: and(i -> i.eq("name", "李白").ne("status", "活着")) ---> and (name = '李白' and status
<> '活着')
测试用例:
/**
* Wrapper条件构造器-- or 或
**/
@Test
public void Or(){
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.eq( "name" , "亚索" ).or().eq( "age" ,20);
List<User> userList = userMapper.selectList(queryWrapper);
// SELECT id,user_name,password,name,age,email FROM tb_user WHERE name = '亚索' OR age = 20
for (User user : userList) {
System.out.println(user);
}
}
select(查询指定字段)
在MP查询中,默认查询所有的字段,如果有需要也可以通过select方法进行指定字段。
这个时候我们就可以使用select去指定查询某些字段了,不查询的字段也会显示出来,但是值为null
测试用例
/**
* Wrapper条件构造器- select查询指定字段
**/
@Test
public void select(){
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.eq( "name" , "亚索" )
.or()
.eq( "age" ,20)
.select( "id" , "user_name" );
List<User> userList = userMapper.selectList(queryWrapper);
// SELECT id,user_name FROM tb_user WHERE name = '亚索' OR age = 20
for (User user : userList) {
System.out.println(user);
}
}