接着 Mybatis Plus 系列3.1 —— Mapper CRUD之查询 我们这章主要讲一下条件构造器。
关于条件构造器,还是先贴一下官网的说明:
- 以下出现的第一个入参
boolean condition
表示该条件是否加入最后生成的sql中,例如:query.like(StringUtils.isNotBlank(name), Entity::getName, name) .eq(age!=null && age >= 0, Entity::getAge, age)
- 以下代码块内的多个方法均为从上往下补全个别
boolean
类型的入参,默认为true
- 以下出现的泛型
Param
均为Wrapper
的子类实例(均具有AbstractWrapper
的所有方法) - 以下方法在入参中出现的
R
为泛型,在普通wrapper中是String
,在LambdaWrapper
中是函数(例:Entity::getId
,Entity
为实体类,getId
为字段id
的getMethod) - 以下方法入参中的
R column
均表示数据库字段,当R
具体类型为String
时则为数据库字段名(字段名是数据库关键字的自己用转义符包裹!)!而不是实体类数据字段名!!!,另当R
具体类型为SFunction
时项目runtime不支持eclipse自家的编译器!!! - 以下举例均为使用普通
wrapper
,入参为Map
和List
的均以json
形式表现! - 使用中如果入参的
Map
或者List
为空,则不会加入最后生成的sql中!!!
还是先看一下Wrapper
的类继承关系:
上一章就说过,我是推荐使用 Lambda 表达式 的方式构建Wrapper
的,所以我们主要使用:LambdaQueryWrapper
和LambdaUpdateWrapper
来做示例,首先看一下类图:
我们按照官网的顺序介绍一条件构造器。
一. AbstractWrapper
QueryWrapper(LambdaQueryWrapper)
和UpdateWrapper(LambdaUpdateWrapper)
的父类
用于生成 sql 的 where 条件, entity 属性也用于生成 sql 的 where 条件
注意: entity 生成的 where 条件与 使用各个 api 生成的 where 条件没有任何关联行
1. eq
等于
eq(R column, Object val) // 底层调的就是 eq(true, column, val);
eq(boolean condition, R column, Object val)
示例:
@Test
@DisplayName("条件构造器1-eq")
public void eqTest1() {
LambdaQueryWrapper<User> eq = Wrappers.<User>lambdaQuery()
.eq(User::getSex, "MAIL")
.eq(User::getIsDelete, false);
List<User> users = userMapper.selectList(eq);
Assertions.assertFalse(users.isEmpty());
}
结果:
==> Preparing: SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE (sex = ? AND is_delete = ?)
==> Parameters: MAIL(String), false(Boolean)
<== Columns: id, name, age, email, sex, is_delete, create_time, update_time
<== Row: 1, Jone, 18, test1@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Row: 2, Jack, 20, test2@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Row: 3, Tom, 28, test3@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Total: 3
这里重点介绍一下重载方法eq(boolean condition, R column, Object val)
这里面有一个condition
( 执行条件)参数,用来控制当前条件是否会加到最终的SQL中去。举个例子:有一个用户查询列表页面,查询条件有”姓名“,”性别“等,如果某个条件没输入,则忽略该条件。这种场景大家应该经非常熟悉,之前我们可以使用mybatis
的动态SQL来实现。这里我们就可以利用condition
条件,比较优雅的实现这个功能。
@Test
@DisplayName("条件构造器2-eq")
public void eqTest2() {
// 模拟输入的查询条件
String name = "jack";
String sex = null;
LambdaQueryWrapper<User> eq = Wrappers.<User>lambdaQuery()
.eq(StringUtils.hasLength(name), User::getName, name) // name 不为空时,使用该条件
.eq(StringUtils.hasLength(sex), User::getSex, sex) // sex 不为空时,使用该条件
.eq(User::getIsDelete, false);
List<User> users = userMapper.selectList(eq);
Assertions.assertFalse(users.isEmpty());
}
结果,可见where条件并没有sex
相关的条件了:
==> Preparing: SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE (name = ? AND is_delete = ?)
==> Parameters: jack(String), false(Boolean)
<== Columns: id, name, age, email, sex, is_delete, create_time, update_time
<== Row: 2, Jack, 20, test2@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Total: 1
对比一下不使用condition
条件的情况:
@Test
@DisplayName("条件构造器2-eq")
public void eqTest2() {
// 模拟输入的查询条件
String name = "jack";
String sex = null;
LambdaQueryWrapper<User> eq = Wrappers.<User>lambdaQuery()
.eq(User::getName, name)
.eq(User::getSex, sex)
.eq(User::getIsDelete, false);
List<User> users = userMapper.selectList(eq);
Assertions.assertTrue(users.isEmpty());
}
结果:
==> Preparing: SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE (name = ? AND sex = ? AND is_delete = ?)
==> Parameters: jack(String), null, false(Boolean)
<== Total: 0
说明:
不仅仅eq
条件有关于condition
的重载方法,其它的也有,使用方式也一样,后面就不再逐个演示了!
2. ne
不等于
ne(R column, Object val) // ne(true, column, val);
ne(boolean condition, R column, Object val)
示例:
@Test
@DisplayName("条件构造器-ne")
public void neTest() {
LambdaQueryWrapper<User> eq = Wrappers.<User>lambdaQuery()
.ne(User::getSex, "MAIL")
.eq(User::getIsDelete, false);
List<User> users = userMapper.selectList(eq);
Assertions.assertFalse(users.isEmpty());
}
结果:
==> Preparing: SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE (sex <> ? AND is_delete = ?)
==> Parameters: MAIL(String), false(Boolean)
<== Columns: id, name, age, email, sex, is_delete, create_time, update_time
<== Row: 4, Sandy, 21, test4@baomidou.com, FEMALE, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Row: 5, Billie, 24, test5@baomidou.com, FEMALE, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Total: 2
3. allEq
全部eq(或个别isNull)
// params : key为数据库字段名, value为字段值
// null2IsNull : 为true则在map的value为null时调用 isNull 方法,为false时则忽略value为null的
// filter : 过滤函数,是否允许字段传入比对条件中
allEq(Map<R, V> params) // 底层调用 allEq(params, true);
allEq(Map<R, V> params, boolean null2IsNull) // 底层调用 allEq(true, params, null2IsNull);
allEq(boolean condition, Map<R, V> params, boolean null2IsNull)
allEq(BiPredicate<R, V> filter, Map<R, V> params) // 底层调用 allEq(filter, params, true)
allEq(BiPredicate<R, V> filter, Map<R, V> params, boolean null2IsNull) // 底层调用 allEq(true, filter, params, null2IsNull)
allEq(boolean condition, BiPredicate<R, V> filter, Map<R, V> params, boolean null2IsNull)
示例1:
@Test
@DisplayName("条件构造器1-allEq")
public void allEqTest1() {
Map<SFunction<User, ?>, Object> param = new HashMap<>();
param.put(User::getSex, "MAIL");
param.put(User::getIsDelete, false);
// param 为 null 或者 empty 则查询全部
LambdaQueryWrapper<User> eq = Wrappers.<User>lambdaQuery().allEq(param);
List<User> users = userMapper.selectList(eq);
Assertions.assertFalse(users.isEmpty());
}
结果:
==> Preparing: SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE (is_delete = ? AND sex = ?)
==> Parameters: false(Boolean), MAIL(String)
<== Columns: id, name, age, email, sex, is_delete, create_time, update_time
<== Row: 1, Jone, 18, test1@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Row: 2, Jack, 20, test2@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Row: 3, Tom, 28, test3@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Total: 3
示例2:
@Test
@DisplayName("条件构造器2-allEq")
public void allEqTest2() {
Map<SFunction<User, ?>, Object> param = new HashMap<>();
param.put(User::getSex, "MAIL");
param.put(User::getIsDelete, null);
LambdaQueryWrapper<User> eq = Wrappers.<User>lambdaQuery()
.allEq(param, false); // 默认null2IsNull 为 true, 此时查询调价会忽略value为null的key
List<User> users = userMapper.selectList(eq);
Assertions.assertFalse(users.isEmpty());
}
结果:
==> Preparing: SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE (sex = ?)
==> Parameters: MAIL(String)
<== Columns: id, name, age, email, sex, is_delete, create_time, update_time
<== Row: 1, Jone, 18, test1@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Row: 2, Jack, 20, test2@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Row: 3, Tom, 28, test3@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Total: 3
示例3:
@Test
@DisplayName("条件构造器3-allEq")
public void allEqTest3() {
SFunction<User, ?> sex = User::getSex;
Map<SFunction<User, ?>, Object> param = new HashMap<>();
param.put(sex, "MAIL");
param.put(User::getIsDelete, false);
LambdaQueryWrapper<User> eq = Wrappers.<User>lambdaQuery()
.allEq((k, v) -> {
// 过滤函数,是否允许字段传入比对条件中
log.info("k = {}, v = {}", k, v);
return sex.equals(k); // 只需要 sex 条件, 如果过滤出来为空(始终返回false),那么则全量查询
}, param); // 默认null2IsNull 为 true, 此时查询调价会忽略value为null的key
List<User> users = userMapper.selectList(eq);
Assertions.assertFalse(users.isEmpty());
}
2021-02-13 12:28:16.153 INFO 40236 --- [ Test worker] c.j.m.demo.demo.UserWrapperTest : k = cn.justmr.mybatisplus.demo.demo.UserWrapperTest$$Lambda$829/1464585291@6e247c30, v = MAIL
2021-02-13 12:28:16.158 INFO 40236 --- [ Test worker] c.j.m.demo.demo.UserWrapperTest : k = cn.justmr.mybatisplus.demo.demo.UserWrapperTest$$Lambda$830/567167554@3f9bd04, v = false
...
==> Preparing: SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE (sex = ?)
==> Parameters: MAIL(String)
<== Columns: id, name, age, email, sex, is_delete, create_time, update_time
<== Row: 1, Jone, 18, test1@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Row: 2, Jack, 20, test2@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Row: 3, Tom, 28, test3@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Total: 3
4. gt
大于
ge(R column, Object val) ge(boolean condition, R column, Object val)
示例:
.gt(User::getAge, 18) ---> age > 18
5. ge
大于等于
ge(R column, Object val) ge(boolean condition, R column, Object val)
示例:
.ge(User::getAge, 18) ---> age >= 18
6. lt
小于
lt(R column, Object val) lt(boolean condition, R column, Object val)
示例:
.lt(User::getAge, 18) ---> age < 18
7. le
小于等于
le(R column, Object val) le(boolean condition, R column, Object val)
示例:
.le(User::getAge, 18) ---> age <= 18
8. between
BETWEEN 值1 AND 值2
between(R column, Object val1, Object val2) between(boolean condition, R column, Object val1, Object val2)
示例:
.between(User::getAge, 18, 20) ---> age BETWEEN 18 AND 20
9. notBetween
NOT BETWEEN 值1 AND 值2
notBetween(R column, Object val1, Object val2) notBetween(boolean condition, R column, Object val1, Object val2)
示例:
.notBetween(User::getAge, 18, 20) ---> age NOT BETWEEN 18 AND 20
10. like
模糊查询
LIKE '%值%'
like(R column, Object val) like(boolean condition, R column, Object val)
示例:
.like(User::getName, "J") ---> name LIKE '%J%'
注意:不需要自己拼接’%’了
11. notLike
NOT LIKE ‘%值%’
notLike(R column, Object val) notLike(boolean condition, R column, Object val)
示例:
.notLike(User::getName, "J") ---> name NOT LIKE '%J%'
12. likeLeft
LIKE ‘%值’
likeLeft(R column, Object val) likeLeft(boolean condition, R column, Object val)
示例:
.likeLeft(User::getName, "J") ---> name LIKE '%J'
13. likeRight
LIKE ‘值%’
likeRight(R column, Object val) likeRight(boolean condition, R column, Object val)
示例:
.likeRight(User::getName, "J") ---> name LIKE 'J%'
14. isNull
字段 IS NULL
isNull(R column) isNull(boolean condition, R column)
示例:
.isNull(User::getName) ---> name IS NULL
15. isNotNull
字段 IS NOT NULL
isNotNull(R column) isNotNull(boolean condition, R column)
示例:
.isNotNull(User::getName) ---> name IS NOT NULL
16. in
字段 IN (value.get(0), value.get(1), …)
in(R column, Collection<?> value) in(boolean condition, R column, Collection<?> value)
示例:
.in(User::getId, Lists.list(1L, 2L)) ---> id IN (1, 2)
注意:
value不能为null,会报错
value不能为空,会报错,例如
SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE id IN ();
这个sql执行报错
17. notIn
字段 NOT IN (value.get(0), value.get(1), …)
notIn(R column, Collection<?> value) notIn(boolean condition, R column, Collection<?> value)
示例:
.notIn(User::getId, Lists.list(1L, 2L)) ---> id NOT IN (1, 2)
18. inSql
字段 IN ( sql语句 )
inSql(R column, String inValue) inSql(boolean condition, R column, String inValue)
- 例:
.inSql(User::getId, "1, 2") --- > id IN (1, 2)
// 会有sql注入风险 - 例:
inSql(User::getId, "select id from table where id < 3") ---> id IN (select id from user where id < 3)
19. notInSql
字段 NOT IN ( sql语句 )
notInSql(R column, String inValue) notInSql(boolean condition, R column, String inValue)
20. groupBy
分组:GROUP BY 字段, …
groupBy(R... columns) groupBy(boolean condition, R... columns)
示例:
.groupBy(User::getSex) ---> GROUP BY sex
21. orderByAsc
排序:ORDER BY 字段, … ASC
orderByAsc(R... columns) orderByAsc(boolean condition, R... columns)
示例:
.orderByAsc(orderByAsc(User::getCreateTime, User::getId)) ---> ORDER BY create_time ASC, id ASC
22. orderByDesc
排序:ORDER BY 字段, … DESC
orderByDesc(R... columns) orderByDesc(boolean condition, R... columns)
示例:
.orderByDesc(orderByAsc(User::getCreateTime, User::getId)) ---> ORDER BY create_time DESC, id DESC
23. orderBy
排序:ORDER BY 字段, …
orderBy(boolean condition, boolean isAsc, R... columns)
示例:
.orderBy(true, true, User::getCreateTime, User::getId) ---> ORDER BY create_time ASC, id ASC
24. having
HAVING ( sql语句 )
having(String sqlHaving, Object... params) having(boolean condition, String sqlHaving, Object... params)
- 例:
having("sum(age) > 10") ---> having sum(age) > 10
- 例:
having("sum(age) > {0}", 11) ---> having sum(age) > 11
25. func
主要方便在出现if…else下调用不同方法能不断链
func(Consumer<Children> consumer) func(boolean condition, Consumer<Children> consumer)
示例1:
@Test
@DisplayName("条件构造器1-apply")
public void applyTest1() {
List<Long> ids = Lists.list(1L);
LambdaQueryWrapper<User> eq = Wrappers.<User>lambdaQuery()
.func(item -> {
if (CollectionUtils.isEmpty(ids)) {
item.apply("1 != 1");
} else {
item.in(User::getId, ids);
}
})
.eq(User::getIsDelete, false)
.orderByAsc(User::getCreateTime);
List<User> users = userMapper.selectList(eq);
Assertions.assertFalse(users.isEmpty());
}
结果:
==> Preparing: SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE (id IN (?) AND is_delete = ?) ORDER BY create_time ASC
==> Parameters: 1(Long), false(Boolean)
<== Columns: id, name, age, email, sex, is_delete, create_time, update_time
<== Row: 1, Jone, 18, test1@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Total: 1
示例2,对比一下示例1:
@Test
@DisplayName("条件构造器2-apply")
public void applyTest2() {
List<Long> ids = Lists.list();
LambdaQueryWrapper<User> eq = Wrappers.<User>lambdaQuery()
.func(item -> {
if (CollectionUtils.isEmpty(ids)) {
item.apply("1 != 1");
} else {
item.in(User::getId, ids);
}
})
.eq(User::getIsDelete, false)
.orderByAsc(User::getCreateTime);
List<User> users = userMapper.selectList(eq);
Assertions.assertTrue(users.isEmpty());
}
结果:
==> Preparing: SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE (1 != 1 AND is_delete = ?) ORDER BY create_time ASC
==> Parameters: false(Boolean)
<== Total: 0
26. or
拼接 OR
主动调用
or
表示紧接着下一个方法不是用and
连接!(不调用or
则默认为使用and
连接)or() or(boolean condition)
示例:
// 1. WHERE id = 1 OR name = 'Jack' AND is_delete = false
.eq(User::getId, 1L)
.or()
.eq(User::getName, "Jack")
.eq(User::getIsDelete, false)
// 2. WHERE id = 1 AND name = 'Jack' AND is_delete = false
.eq(User::getId, 1L)
.or(false)
.eq(User::getName, "Jack")
.eq(User::getIsDelete, false);
or嵌套
or(Consumer<Param> consumer) or(boolean condition, Consumer<Param> consumer)
示例:
// 1. WHERE (id = ? OR (name = ? AND email = ?) AND is_delete = ?)
.eq(User::getId, 1L)
.or(i -> i.eq(User::getName, "JACK").eq(User::getEmail, "22@qq.com"))
.eq(User::getIsDelete, false);
// 2. WHERE (id = ? AND is_delete = ?)
.eq(User::getId, 1L)
.or(false, i -> i.eq(User::getName, "JACK").eq(User::getEmail, "22@qq.com"))
.eq(User::getIsDelete, false);
27. and
AND 嵌套
and(Consumer<Param> consumer) and(boolean condition, Consumer<Param> consumer)
示例:
// WHERE (name = ? AND (age = ? OR age = ?) AND is_delete = ?)
.eq(User::getName, "Jack")
.and(i -> i.eq(User::getAge, 18).or().eq(User::getAge, 21))
.eq(User::getIsDelete, false);
28. nested
正常嵌套 不带 AND 或者 OR
>nested(Consumer<Param> consumer) >nested(boolean condition, Consumer<Param> consumer)
示例:
// WHERE (name = ? AND (age = ? OR age = ?) AND is_delete = ?)
.eq(User::getName, "Jack")
.nested(i -> i.eq(User::getAge, 18).or().eq(User::getAge, 21))
.eq(User::getIsDelete, false);
29. apply
拼接 sql
该方法可用于数据库函数 动态入参的
params
对应前面applySql
内部的{index}
部分.这样是不会有sql注入风险的,反之会有!apply(String applySql, Object... params) apply(boolean condition, String applySql, Object... params)
示例:
- 例:
apply("id = 1")
—>id = 1
- 例:
apply("date_format(dateColumn,'%Y-%m-%d') = '2008-08-08'")
—>date_format(dateColumn,'%Y-%m-%d') = '2008-08-08'")
- 例:
apply("date_format(dateColumn,'%Y-%m-%d') = {0}", "2008-08-08")
—>date_format(dateColumn,'%Y-%m-%d') = '2008-08-08'")
30. last
无视优化规则直接拼接到 sql 的最后
只能调用一次,多次调用以最后一次为准 有sql注入的风险,请谨慎使用
last(String lastSql) last(boolean condition, String lastSql)
使用的较多的就是last("limit 1")
@Test
@DisplayName("条件构造器-last")
public void lastTest() {
LambdaQueryWrapper<User> eq = Wrappers.<User>lambdaQuery()
.gt(User::getAge, 18)
.eq(User::getIsDelete, false)
.orderByDesc(User::getAge)
.last("limit 1");
User user = userMapper.selectOne(eq);
Assertions.assertTrue(user != null);
}
结果:
==> Preparing: SELECT id,name,age,email,sex,is_delete,create_time,update_time FROM user WHERE (age > ? AND is_delete = ?) ORDER BY age DESC limit 1
==> Parameters: 18(Integer), false(Boolean)
<== Columns: id, name, age, email, sex, is_delete, create_time, update_time
<== Row: 3, Tom, 28, test3@baomidou.com, MAIL, 0, 2021-02-12 22:43:00, 2021-02-12 22:43:00
<== Total: 1
31. exists
拼接 EXISTS ( sql语句 )
exists(String existsSql) exists(boolean condition, String existsSql)
示例:
exists("select id from table where age = 1") ---> exists (select id from table where age = 1)
32. notExists
拼接 NOT EXISTS ( sql语句 )
notExists(String notExistsSql) notExists(boolean condition, String notExistsSql)
示例:
notExists("select id from table where age = 1") ---> not exists (select id from table where age = 1)
二. QueryWrapper
继承自 AbstractWrapper ,自身的内部属性 entity 也用于生成 where 条件
及 LambdaQueryWrapper, 可以通过 new QueryWrapper().lambda() 方法获取
1. select
设置查询字段
select(String... sqlSelect)
select(Predicate<TableFieldInfo> predicate)
select(Class<T> entityClass, Predicate<TableFieldInfo> predicate)
以上方法分为两类.
第二类方法为:过滤查询字段(主键除外),入参不包含 class 的调用前需要wrapper
内的entity
属性有值! 这两类方法重复调用以最后一次为准
示例:
// 1. SELECT id,name FROM user WHERE (is_delete = ?)
QueryWrapper<User> eq = Wrappers.<User>query()
.select("id", "name")
.eq("is_delete", false);
List<User> users = userMapper.selectList(eq);
// 2. ELECT id,name FROM user WHERE (is_delete = ?)
QueryWrapper<User> eq = Wrappers.<User>query()
.setEntityClass(User.class) // 必要
.select(i -> i.getProperty().equals("name"))
.eq("is_delete", false);
List<User> users = userMapper.selectList(eq);
// 3. SELECT id,name FROM user WHERE (is_delete = ?)
QueryWrapper<User> eq = Wrappers.<User>query()
.select(User.class, i -> i.getProperty().equals("name"))
.eq("is_delete", false);
List<User> users = userMapper.selectList(eq);
2. lambda
获取
LambdaQueryWrapper
示例:
LambdaQueryWrapper<User> eq = Wrappers.<User>query().lambda()
.select(User::getId, User::getName)
.eq(User::getIsDelete, false);
三. UpdateWrapper
继承自
AbstractWrapper
,自身的内部属性entity
也用于生成 where 条件
及LambdaUpdateWrapper
, 可以通过new UpdateWrapper().lambda()
方法获取!
1. set
QL SET 字段
set(String column, Object val) set(boolean condition, String column, Object val)
示例:
set("name", "老李头")
示例: set("name", "")
—>数据库字段值变为空字符串
示例:set("name", null)
—>数据库字段值变为null
2. setSql
设置 SET 部分 SQL
setSql(String sql)
示例:
setSql("name = '老李头'")
3. lambda
获取
LambdaUpdateWrapper
示例:
LambdaUpdateWrapper<User> eq = Wrappers.<User>update().lambda()
.set(User::getEmail, "33@qq.com")
.eq(User::getId, 1L);