其他网址
条件构造器queryWrapper、updateWrapper_QingFeng-Li的博客-CSDN博客_querywrapper
Mybatis plus学习笔记(常用注解/条件构造器) - 知乎
条件示例大全
函数名 | 说明 | 说明/例子 |
allEq | 全部eq(或个别isNull) | 例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 = '老王' |
Wrapper类的关系
介绍 :
上图绿色框为抽象类abstract
蓝色框为正常class类,可new对象
黄色箭头指向为父子类关系,箭头指向为父类
wapper介绍 :
Wrapper : 条件构造抽象类,最顶端父类,抽象类中提供4个方法西面贴源码展示
AbstractWrapper : 用于查询条件封装,生成 sql 的 where 条件
AbstractLambdaWrapper : Lambda 语法使用 Wrapper统一处理解析 lambda 获取 column。
LambdaQueryWrapper :看名称也能明白就是用于Lambda语法使用的查询Wrapper
LambdaUpdateWrapper : Lambda 更新封装Wrapper
QueryWrapper : Entity 对象封装操作类,不是用lambda语法
UpdateWrapper : Update 条件封装,用于Entity对象更新操作
通过设置实体类的值来查询:若某一项设置为null,则不会拼接sql。
通过Map和allEq来查询:若某一项设置为null,则会拼接sql。(若想过滤null项,allEq的第二个参数设为false)
查询名字叫“Tony”的,年龄等于20的。seletOne返回的是一条实体记录,当出现多条时会报错。
如果需要有多条记录时只取一条,可以使用IService.java的getOne(Wrapper
, Boolean)方法,指定第二个参数为false。
传实体类
public void testSelectList() { User user = new User(); user.setName("张"); user.setAge(28); user.setLastName(null); QueryWrapper
queryWrapper = new QueryWrapper<>(user); //User user = userMapper.selectOne(queryWrapper); //查询一条记录 //System.out.println(user); List users = userMapper.selectList(queryWrapper); users.forEach(System.out::println); } 执行结果
==> Preparing: SELECT id,name,last_name,email,gender,age FROM tb_user WHERE name=? AND age=? ==> Parameters: 张(String), 28(Integer) <== Total: 0
直接用eq
public void testSelectEqList() { QueryWrapper
queryWrapper = new QueryWrapper<>(); // queryWrapper.eq("name", "张三").eq("age", 28).eq("last_name", null); //这样也可以 queryWrapper.eq("name", "张三"); queryWrapper.eq("age", 28); queryWrapper.eq("last_name", null); List users = userMapper.selectList(queryWrapper); users.forEach(System.out::println); } 执行结果
==> Preparing: SELECT id,name,last_name,email,gender,age FROM tb_user WHERE (name = ? AND age = ? AND last_name = ?) ==> Parameters: 张三(String), 28(Integer), null <== Total: 0
Map+allEq
public void selectWrapper13() { QueryWrapper
queryWrapper = new QueryWrapper<>(); Map map = new HashMap<>(); // 普通查询 map.put("name", "张三"); map.put("age",28); map.put("last_name",null); queryWrapper.allEq(map); // queryWrapper.allEq(map, false);// 传入false自动过滤为null的 // 自动过滤name参数 //queryWrapper.allEq((key, value) -> !key.equals("name"), map); //User user = userMapper.selectOne(queryWrapper); //查询一条记录 //System.out.println(user); List users = userMapper.selectList(queryWrapper); users.forEach(System.out::println); } 执行结果
==> Preparing: SELECT id,name,last_name,email,gender,age FROM tb_user WHERE (name = ? AND last_name IS NULL AND age = ?) ==> Parameters: 张三(String), 28(Integer) <== Total: 0
传入false执行结果
==> Preparing: SELECT id,name,last_name,email,gender,age FROM tb_user WHERE (name = ? AND age = ?) ==> Parameters: 张三(String), 28(Integer) <== Total: 0
返回需要的字段(法1)
返回多个列
public void selectWrapper09() { QueryWrapper
queryWrapper = new QueryWrapper<>(); queryWrapper.select("name", "age", "phone").likeRight("name", "王").le("age", 30); List users = userMapper.selectList(queryWrapper); users.forEach(System.out::println); }
注意,返回单个列时,不能直接赋值给List
,因为userMapper对应的泛型是User实体, 返回时的泛型也是List 。如果想返回List ,必须自定义SQL,将实体直接定为Object。
返回需要的字段(法2)
public void selectWrapper12() { User user = new User(); user.setName("张"); user.setAge(28); QueryWrapper
queryWrapper = new QueryWrapper<>(user, "id", "last_name"); List users = userMapper.selectList(queryWrapper); users.forEach(System.out::println); }
执行结果
==> Preparing: SELECT id,last_name FROM tb_user WHERE name=? AND age=? ==> Parameters: 张(String), 28(Integer) <== Total: 0
过滤不需要的字段
public void selectWrapper10() { QueryWrapper
queryWrapper = new QueryWrapper<>(); queryWrapper.select(User.class, p -> !p.getColumn().equals("parent_id") && !p.getColumn().equals("create_time")).likeRight("name", "王"); List users = userMapper.selectList(queryWrapper); users.forEach(System.out::println); }
private void condition(String name, String email) { QueryWrapper
wrapper = new QueryWrapper<>(); //需要六行,太麻烦 // if(StringUtils.isNotBlank(name)){ // wrapper.like("name",name); // } // if(StringUtils.isNotBlank(name)){ // wrapper.like("name",name); // } wrapper.like(StringUtils.isNotBlank("name"), "name", name) .like(StringUtils.isNotBlank("email"), "email", email); List users = userMapper.selectList(wrapper); for (User user : users) { System.out.println(user.toString()); } }
根据 Wrapper 条件,查询总记录数
public void selectCount() { QueryWrapper
queryWrapper = new QueryWrapper<>(); queryWrapper.eq("name", "lqf"); Integer count = userMapper.selectCount(queryWrapper); System.out.println(count); }
根据 wrapper 条件,查询全部记录
queryWrapper 实体对象封装操作类(可以为 null)为null查询全部
public void selectList() { List
list = userMapper.selectList(null); System.out.println(list); }
根据 Wrapper 条件,返回maps
queryWrapper 实体对象封装操作类(可以为 null)
public void testSelectNull() { QueryWrapper
queryWrapper = new QueryWrapper<>(null); List
打印结果
{gender=1, last_name=东方不败, id=321eece6b1620ab97123785edbdef490, [email protected], age=20} {gender=1, last_name=Tony, id=101eece6b1620ab97ffa8c8edbdef490, [email protected], age=20} {gender=2, last_name=Pepper, id=9d532cbadd8ea0beb7ea5a7c867bc863, [email protected], age=20}
多条件查询
查询姓王的,年龄大于等于20,小于等于40.并且email不为空
public void selectWrapper01() { QueryWrapper queryWrapper = new QueryWrapper(); queryWrapper.likeRight("name", "王"); queryWrapper.between("age", 20, 40); queryWrapper.isNotNull("email"); List list = userMapper.selectList(queryWrapper); list.forEach(System.out::println); }
多条件查询并排序
查询姓王的,或者年龄大于30。按照年龄降序,如果年龄相同按照id升序
public void selectWrapper02() { QueryWrapper queryWrapper = new QueryWrapper(); queryWrapper.likeRight("name", "王"); queryWrapper.or(); queryWrapper.ge("age", 30); queryWrapper.orderByDesc("age"); queryWrapper.orderByAsc("id"); List list = userMapper.selectList(queryWrapper); list.forEach(System.out::println); }
多条件查询(and)
名字为王姓,并且年龄小于40或邮箱不为空
public void selectWrapper04() { QueryWrapper
queryWrapper = new QueryWrapper<>(); queryWrapper.likeRight("name", "王"); queryWrapper.and(qw -> qw.lt("age", 40).or().isNotNull("email")); List list = userMapper.selectList(queryWrapper); list.forEach(System.out::println); }
多条件查询(nested)
(年龄小于40或邮箱不为空),并且名字为王姓
public void selectWrapper06() { QueryWrapper
queryWrapper = new QueryWrapper<>(); queryWrapper.nested(qw -> qw.lt("age", 40).or().isNotNull("email")).likeRight("name", "王"); List users = userMapper.selectList(queryWrapper); users.forEach(System.out::println); }
模拟in查询
public void selectWrapper07() { QueryWrapper
queryWrapper = new QueryWrapper<>(); queryWrapper.in("age", Arrays.asList(21, 26, 28)); List users = userMapper.selectList(queryWrapper); users.forEach(System.out::println); }
根据 entity 条件,删除记录
QueryWrapper实体对象封装操作类(可以为 null),下方获取到queryWrapper后删除的查询条件为name字段为null的and年龄大于等于12的and email字段不为null的
public void delete() { QueryWrapper
queryWrapper = new QueryWrapper<>(); queryWrapper .isNull("name") .ge("age", 12) .isNotNull("email"); int delete = userMapper.delete(queryWrapper); System.out.println("delete return count = " + delete); }
根据 entity 条件,查询全部记录(并翻页)
page 分页查询条件(可以为 RowBounds.DEFAULT)
queryWrapper 实体对象封装操作类(可以为 null)
public void selectPage() { Page
page = new Page<>(1, 5); QueryWrapper queryWrapper = new QueryWrapper<>(); IPage userIPage = userMapper.selectPage(page, queryWrapper); System.out.println(userIPage); } //需要在项目中加入分页插件 @Bean public PaginationInterceptor paginationInterceptor() { return new PaginationInterceptor(); }
打印结果
==> Preparing: SELECT COUNT(1) FROM user
==> Parameters:
<== Columns: COUNT(1)
<== Row: 100
==> Preparing: SELECT id,name,age,email,status FROM user LIMIT 0,5
==> Parameters:
<== Columns: id, name, age, email, status
<== Row: 1046282328366391319, lqf, 12, [email protected], 0
<== Row: 1046282328366391320, lqf, 12, [email protected], 0
<== Row: 1046282328366391321, lqf, 12, [email protected], 0
<== Row: 1046282328366391322, lqf, 12, [email protected], 0
<== Row: 1046282328366391323, lqf, 12, [email protected], 0
<== Total: 5
根据 Wrapper 条件,查询全部记录(并翻页)
page 分页查询条件
queryWrapper 实体对象封装操作类
和上个分页同理只是返回类型不同
public void selectMapsPage() { Page
page = new Page<>(1, 5); QueryWrapper queryWrapper = new QueryWrapper<>(); IPage
LambdaQueryWrapper的好处
从下边例子中可以看出,不需要创建User对象,也不需要手动找到对应的字段名,直接用User::xxx即可
多个条件查询(名字中带“张”且年龄小于30岁)
public void selectWrapper15() { // 方式一 LambdaQueryWrapper
lambda = new QueryWrapper ().lambda(); // 方式二 LambdaQueryWrapper lambda2 = new LambdaQueryWrapper<>(); // 方式三 LambdaQueryWrapper lambda3 = Wrappers. lambdaQuery(); lambda3.like(User::getName, "张").lt(User::getAge, 30); List users = userMapper.selectList(lambda3); users.forEach(System.out::println); }
多个条件查询:王姓并且(年龄小于40或邮箱不为空)
public void selectWrapper16() { LambdaQueryWrapper
wq = Wrappers. lambdaQuery(); wq.like(User::getName, "张").and(user -> user.lt(User::getAge, 40).or().isNotNull(User::getEmail)); List users = userMapper.selectList(wq); users.forEach(System.out::println); }
多个条件查询:王姓并且年龄小于40
public void selectWrapper17() { List
users = new LambdaQueryChainWrapper (userMapper).like(User::getName, "张").lt(User::getAge, 40).list(); users.forEach(System.out::println); }
简介
前面的查询都是创建一个条件构造器,再通过mapper或service以条件构造器为参数进行查询。LambdaQueryChainWrapper将前面的两句合二为一,一句来完成带条件的查询。
创建LambdaQueryChainWrapper对象需要传递mapper对象。只有list()和one()两个方法获取数据,返回的都是实体对象或实体对象的集合,没有对应的Map()查询方法。
one():若存在多个结果,则报异常。此方法只能用于只有一个结果的情况。
public void contextLoads() {
List list = new LambdaQueryChainWrapper(userMapper)
.select(User::getId, User::getName)
.like(User::getName, "王").list();
System.out.println(list);
}
可用的查询
可用的比较
根据 Entity 条件,更新记录
entity 实体对象 (set 条件值,不能为 null)
updateWrapper 实体对象封装操作类(可以为 null,里面的 entity 用于生成 where 语句)
public void update() { //修改值 User user = new User(); user.setStatus(true); user.setName("zhangsan"); //修改条件 UpdateWrapper
userUpdateWrapper = new UpdateWrapper<>(); userUpdateWrapper.eq("name", "lqf"); userUpdateWrapper.eq("email", "[email protected]"); int update = userMapper.update(user, userUpdateWrapper); System.out.println(update); }
打印结果 ==> Preparing: UPDATE user SET name=?, status=? WHERE name = ? ==> Parameters: zhangsan(String), true(Boolean), lqf(String) <== Updates: 100 Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@56a4f272] 100 2018-10-02 15:08:03.928 INFO 7972 --- [ Thread-2] o.s.w.c.s.GenericWebApplicationContext : Closing org.springframework.web.context.support.GenericWebApplicationContext@37313c65: startup date [Tue Oct 02 15:08:00 CST 2018]; root of context hierarchy 2018-10-02 15:08:03.937 INFO 7972 --- [ Thread-2] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Shutdown initiated... 2018-10-02 15:08:04.053 INFO 7972 --- [ Thread-2] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Shutdown completed. Process finished with exit code 0
不构造实体对象
假设只更新一个字段,使用updateWrapper 的构造器时也需构造一个实体对象,这样比较麻烦。可用updateWrapper的set
方法
UpdateWrapper updateWrapper = new UpdateWrapper<>();
updateWrapper.eq("name","shimin").set("age", 35);
Integer rows = userMapper.update(null, updateWrapper);
简介
数据更新相关的构造器(UpdateWrapper、LambdaUpdateWrapper、LambdaUpdateChainWrapper)使用方法类似于查询构造器(QueryWrapper、LambdaQueryWrapper、LambdaQueryChainWrapper),不同的是它增加了如下两个方法:
- set:设置数据库字段值
- setSql:设置 set 部分的 sql
LambdaUpdateWrapper lambdaUpdateWrapper = new LambdaUpdateWrapper<>();
lambdaUpdateWrapper.eq(User::getName, "shimin").set(User::getAge, 34);
Integer rows = userMapper.update(null, lambdaUpdateWrapper);
简介
- 本Wrapper只可更新数据。
- 典型用法是自定义Service并继承ServiceImpl,实现IService,然后自定义service实例直接用lambdaUpdate方法取得
- 所在包为:com.baomidou.mybatisplus.extension.conditions.update
(另一个包已标记为deprecated:com.baomidou.mybatisplus.extension.service.additional.update.impl)
更新数据:
LambdaUpdateChainWrapper lambdaUpdateChainWrapper = new LambdaUpdateChainWrapper<>(userMapper);
boolean update = lambdaUpdateChainWrapper.eq(User::getName, "Iron Man").set(User::getAge, 20).update();
可用的更新