持久层接口
本文详细介绍了 MyBatis-Plus 进行持久化操作的各种方法,包括插入、更新、删除、查询和分页等。通过本文,您可以了解到 MyBatis-Plus 提供的各种方法是如何进行数据操作的,以及它们对应的 SQL 语句。
Service Interface
IService 是 MyBatis-Plus 提供的一个通用 Service 层接口,它封装了常见的 CRUD 操作,包括插入、删除、查询和分页等。通过继承 IService 接口,可以快速实现对数据库的基本操作,同时保持代码的简洁性和可维护性。
IService 接口中的方法命名遵循了一定的规范,如 get 用于查询单行,remove 用于删除,list 用于查询集合,page 用于分页查询,这样可以避免与 Mapper 层的方法混淆。
save
// 插入一条记录(选择字段,策略插入)boolean save(T entity);// 插入(批量)boolean saveBatch(Collection<T> entityList);// 插入(批量)boolean saveBatch(Collection<T> entityList, int batchSize);
功能描述: 插入记录,根据实体对象的字段进行策略性插入。
返回值: boolean,表示插入操作是否成功。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
T | entity | 实体对象 |
Collection<T> | entityList | 实体对象集合 |
int | batchSize | 插入批次数量 |
示例(save):
// 假设有一个 User 实体对象User user = new User();user.setName("John Doe");user.setEmail("john.doe@example.com");boolean result = userService.save(user); // 调用 save 方法if (result) { System.out.println("User saved successfully.");} else { System.out.println("Failed to save user.");}
生成的 SQL:
INSERT INTO user (name, email) VALUES ('John Doe', 'john.doe@example.com')
示例(saveBatch):
// 假设有一组 User 实体对象List<User> users = Arrays.asList( new User("Alice", "alice@example.com"), new User("Bob", "bob@example.com"), new User("Charlie", "charlie@example.com"));// 使用默认批次大小进行批量插入boolean result = userService.saveBatch(users); // 调用 saveBatch 方法,默认批次大小if (result) { System.out.println("Users saved successfully.");} else { System.out.println("Failed to save users.");}
生成的 SQL(假设默认批次大小为 3):
INSERT INTO user (name, email) VALUES('Alice', 'alice@example.com'),('Bob', 'bob@example.com'),('Charlie', 'charlie@example.com')
示例(saveBatch 指定批次大小):
// 假设有一组 User 实体对象List<User> users = Arrays.asList( new User("David", "david@example.com"), new User("Eve", "eve@example.com"), new User("Frank", "frank@example.com"), new User("Grace", "grace@example.com"));// 指定批次大小为 2进行批量插入boolean result = userService.saveBatch(users, 2); // 调用 saveBatch 方法,指定批次大小if (result) { System.out.println("Users saved successfully.");} else { System.out.println("Failed to save users.");}
生成的 SQL(指定批次大小为 2):
-- 第一批次INSERT INTO user (name, email) VALUES('David', 'david@example.com'),('Eve', 'eve@example.com')
-- 第二批次INSERT INTO user (name, email) VALUES('Frank', 'frank@example.com'),('Grace', 'grace@example.com')
通过上述示例,我们可以看到 save 系列方法是如何在 Service 层进行批量插入操作的,以及它们对应的 SQL 语句。这些方法大大简化了插入操作的代码编写,提高了开发效率。
saveOrUpdate
// TableId 注解属性值存在则更新记录,否插入一条记录boolean saveOrUpdate(T entity);// 根据updateWrapper尝试更新,否继续执行saveOrUpdate(T)方法boolean saveOrUpdate(T entity, Wrapper<T> updateWrapper);// 批量修改插入boolean saveOrUpdateBatch(Collection<T> entityList);// 批量修改插入boolean saveOrUpdateBatch(Collection<T> entityList, int batchSize);
功能描述: 根据实体对象的主键 ID 进行判断,存在则更新记录,否则插入记录。
返回值: boolean,表示插入或更新操作是否成功。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
T | entity | 实体对象 |
Wrapper<T> | updateWrapper | 实体对象封装操作类 UpdateWrapper |
Collection<T> | entityList | 实体对象集合 |
int | batchSize | 插入批次数量 |
示例(saveOrUpdate):
// 假设有一个 User 实体对象,其中 id 是 TableId 注解的属性User user = new User();user.setId(1);user.setName("John Doe");user.setEmail("john.doe@example.com");boolean result = userService.saveOrUpdate(user); // 调用 saveOrUpdate 方法if (result) { System.out.println("User updated or saved successfully.");} else { System.out.println("Failed to update or save user.");}
生成的 SQL(假设 id 为 1 的记录已存在):
UPDATE user SET name = 'John Doe', email = 'john.doe@example.com' WHERE id = 1
生成的 SQL(假设 id 为 1 的记录不存在):
INSERT INTO user (id, name, email) VALUES (1, 'John Doe', 'john.doe@example.com')
示例(saveOrUpdateBatch):
// 假设有一组 User 实体对象,每个对象都有 id 属性List<User> users = Arrays.asList( new User(1, "Alice", "alice@example.com"), new User(2, "Bob", "bob@example.com"), new User(3, "Charlie", "charlie@example.com"));// 使用默认批次大小进行批量修改插入boolean result = userService.saveOrUpdateBatch(users); // 调用 saveOrUpdateBatch 方法,默认批次大小if (result) { System.out.println("Users updated or saved successfully.");} else { System.out.println("Failed to update or save users.");}
生成的 SQL(假设 id 为 1 和 2 的记录已存在,id 为 3 的记录不存在):
UPDATE user SET name = 'Alice', email = 'alice@example.com' WHERE id = 1UPDATE user SET name = 'Bob', email = 'bob@example.com' WHERE id = 2INSERT INTO user (id, name, email) VALUES (3, 'Charlie', 'charlie@example.com')
示例(saveOrUpdateBatch 指定批次大小):
// 假设有一组 User 实体对象List<User> users = Arrays.asList( new User(4, "David", "david@example.com"), new User(5, "Eve", "eve@example.com"), new User(6, "Frank", "frank@example.com"));// 指定批次大小为 2进行批量修改插入boolean result = userService.saveOrUpdateBatch(users, 2); // 调用 saveOrUpdateBatch 方法,指定批次大小if (result) { System.out.println("Users updated or saved successfully.");} else { System.out.println("Failed to update or save users.");}
生成的 SQL(假设指定批次大小为 2):
-- 第一批次UPDATE user SET name = 'David', email = 'david@example.com' WHERE id = 4UPDATE user SET name = 'Eve', email = 'eve@example.com' WHERE id = 5
-- 第二批次INSERT INTO user (id, name, email) VALUES (6, 'Frank', 'frank@example.com')
通过上述示例,我们可以看到 saveOrUpdate 系列方法是如何在 Service 层进行批量修改插入操作的,以及它们对应的 SQL 语句。这些方法提供了高效的数据操作方式,可以根据不同的条件进行更新或插入操作。
remove
// 根据 queryWrapper 设置的条件,删除记录boolean remove(Wrapper<T> queryWrapper);// 根据 ID 删除boolean removeById(Serializable id);// 根据 columnMap 条件,删除记录boolean removeByMap(Map<String, Object> columnMap);// 删除(根据ID 批量删除)boolean removeByIds(Collection<? extends Serializable> idList);
功能描述: 通过指定条件删除符合条件的记录。
返回值: boolean,表示删除操作是否成功。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
Wrapper<T> | queryWrapper | 实体包装类 QueryWrapper |
Serializable | id | 主键 ID |
Map<String, Object> | columnMap | 表字段 map 对象 |
Collection<? extends Serializable> | idList | 主键 ID 列表 |
示例(remove):
// 假设有一个 QueryWrapper 对象,设置删除条件为 name = 'John Doe'QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.eq("name", "John Doe");boolean result = userService.remove(queryWrapper); // 调用 remove 方法if (result) { System.out.println("Record deleted successfully.");} else { System.out.println("Failed to delete record.");}
生成的 SQL:
DELETE FROM user WHERE name = 'John Doe'
示例(removeById):
// 假设要删除 ID 为 1 的用户boolean result = userService.removeById(1); // 调用 removeById 方法if (result) { System.out.println("User deleted successfully.");} else { System.out.println("Failed to delete user.");}
生成的 SQL:
DELETE FROM user WHERE id = 1
示例(removeByMap):
// 假设有一个 columnMap,设置删除条件为 age = 30Map<String, Object> columnMap = new HashMap<>();columnMap.put("age", 30);boolean result = userService.removeByMap(columnMap); // 调用 removeByMap 方法if (result) { System.out.println("Records deleted successfully.");} else { System.out.println("Failed to delete records.");}
生成的 SQL:
DELETE FROM user WHERE age = 30
示例(removeByIds):
// 假设有一组 ID 列表,批量删除用户List<Integer> ids = Arrays.asList(1, 2, 3);boolean result = userService.removeByIds(ids); // 调用 removeByIds 方法if (result) { System.out.println("Users deleted successfully.");} else { System.out.println("Failed to delete users.");}
生成的 SQL:
DELETE FROM user WHERE id IN (1, 2, 3)
通过上述示例,我们可以看到 remove 系列方法是如何在 Service 层进行删除操作的,以及它们对应的 SQL 语句。这些方法提供了灵活的数据操作方式,可以根据不同的条件进行删除操作。
update
// 根据 UpdateWrapper 条件,更新记录 需要设置sqlsetboolean update(Wrapper<T> updateWrapper);// 根据 whereWrapper 条件,更新记录boolean update(T updateEntity, Wrapper<T> whereWrapper);// 根据 ID 选择修改boolean updateById(T entity);// 根据ID 批量更新boolean updateBatchById(Collection<T> entityList);// 根据ID 批量更新boolean updateBatchById(Collection<T> entityList, int batchSize);
功能描述: 通过指定条件更新符合条件的记录。
返回值: boolean,表示更新操作是否成功。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
Wrapper<T> | updateWrapper | 实体对象封装操作类 UpdateWrapper |
T | entity | 实体对象 |
Collection<T> | entityList | 实体对象集合 |
int | batchSize | 更新批次数量 |
示例(update UpdateWrapper 形式):
// 假设有一个 UpdateWrapper 对象,设置更新条件为 name = 'John Doe',更新字段为 emailUpdateWrapper<User> updateWrapper = new UpdateWrapper<>();updateWrapper.eq("name", "John Doe").set("email", "john.doe@newdomain.com");boolean result = userService.update(updateWrapper); // 调用 update 方法if (result) { System.out.println("Record updated successfully.");} else { System.out.println("Failed to update record.");}
生成的 SQL:
UPDATE user SET email = 'john.doe@newdomain.com' WHERE name = 'John Doe'
示例(update WhereWrapper 形式):
// 假设有一个 User 实体对象,设置更新字段为 name,以及一个 whereWrapper 设置更新条件为 id = 1User updateEntity = new User();updateEntity.setName("Updated Name");QueryWrapper<User> whereWrapper = new QueryWrapper<>();whereWrapper.eq("id", 1);boolean result = userService.update(updateEntity, whereWrapper); // 调用 update 方法if (result) { System.out.println("Record updated successfully.");} else { System.out.println("Failed to update record.");}
生成的 SQL:
UPDATE user SET name = 'Updated Name' WHERE id = 1
示例(updateById):
// 假设有一个 User 实体对象,设置更新字段为 email,根据 ID 更新User updateEntity = new User();updateEntity.setId(1);updateEntity.setEmail("updated.email@example.com");boolean result = userService.updateById(updateEntity); // 调用 updateById 方法if (result) { System.out.println("Record updated successfully.");} else { System.out.println("Failed to update record.");}
生成的 SQL:
UPDATE user SET email = 'updated.email@example.com' WHERE id = 1
示例(updateBatchById):
// 假设有一组 User 实体对象,批量更新List<User> users = Arrays.asList( new User(1, null, "new.email1@example.com"), new User(2, null, "new.email2@example.com"));boolean result = userService.updateBatchById(users); // 调用 updateBatchById 方法,默认批次大小if (result) { System.out.println("Records updated successfully.");} else { System.out.println("Failed to update records.");}
生成的 SQL(假设默认批次大小为 2):
UPDATE user SET email = 'new.email1@example.com' WHERE id = 1UPDATE user SET email = 'new.email2@example.com' WHERE id = 2
示例(updateBatchById 指定批次大小):
// 假设有一组 User 实体对象,批量更新,并指定批次大小为 1List<User> users = Arrays.asList( new User(1, null, "new.email1@example.com"), new User(2, null, "new.email2@example.com"));boolean result = userService.updateBatchById(users, 1); // 调用 updateBatchById 方法,指定批次大小if (result) { System.out.println("Records updated successfully.");} else { System.out.println("Failed to update records.");}
生成的 SQL(假设指定批次大小为 1):
-- 第一批次UPDATE user SET email = 'new.email1@example.com' WHERE id = 1-- 第二批次UPDATE user SET email = 'new.email2@example.com' WHERE id = 2
通过上述示例,我们可以看到 update
系列方法是如何在 Service 层进行更新操作的,以及它们对应的 SQL 语句。这些方法提供了灵活的数据操作方式,可以根据不同的条件进行更新操作。
get
// 根据 ID 查询T getById(Serializable id);// 根据 Wrapper,查询一条记录。结果集,如果是多个会抛出异常,随机取一条加上限制条件 wrapper.last("LIMIT 1")T getOne(Wrapper<T> queryWrapper);// 根据 Wrapper,查询一条记录T getOne(Wrapper<T> queryWrapper, boolean throwEx);// 根据 Wrapper,查询一条记录Map<String, Object> getMap(Wrapper<T> queryWrapper);// 根据 Wrapper,查询一条记录<V> V getObj(Wrapper<T> queryWrapper, Function<? super Object, V> mapper);
功能描述: 根据指定条件查询符合条件的记录。
返回值: 查询结果,可能是实体对象、Map 对象或其他类型。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
Serializable | id | 主键 ID |
Wrapper<T> | queryWrapper | 实体对象封装操作类 QueryWrapper |
boolean | throwEx | 有多个 result 是否抛出异常 |
T | entity | 实体对象 |
Function<? super Object, V> | mapper | 转换函数 |
示例(getById):
// 假设要查询 ID 为 1 的用户User user = userService.getById(1); // 调用 getById 方法if (user != null) { System.out.println("User found: " + user);} else { System.out.println("User not found.");}
生成的 SQL:
SELECT * FROM user WHERE id = 1
示例(getOne):
// 假设有一个 QueryWrapper 对象,设置查询条件为 name = 'John Doe'QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.eq("name", "John Doe");User user = userService.getOne(queryWrapper); // 调用 getOne 方法if (user != null) { System.out.println("User found: " + user);} else { System.out.println("User not found.");}
生成的 SQL:
SELECT * FROM user WHERE name = 'John Doe'
示例(getOne 不抛出异常):
// 假设有一个 QueryWrapper 对象,设置查询条件为 name = 'John Doe',并且不抛出异常QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.eq("name", "John Doe");User user = userService.getOne(queryWrapper, false); // 调用 getOne 方法if (user != null) { System.out.println("User found: " + user);} else { System.out.println("User not found.");}
生成的 SQL:
SELECT * FROM user WHERE name = 'John Doe'
示例(getMap):
// 假设有一个 QueryWrapper 对象,设置查询条件为 name = 'John Doe',并将结果映射为 MapQueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.eq("name", "John Doe");Map<String, Object> userMap = userService.getMap(queryWrapper); // 调用 getMap 方法if (userMap != null) { System.out.println("User found: " + userMap);} else { System.out.println("User not found.");}
生成的 SQL:
SELECT * FROM user WHERE name = 'John Doe'
示例(getObj):
// 假设有一个 QueryWrapper 对象,设置查询条件为 name = 'John Doe',并将结果转换为 StringQueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.eq("name", "John Doe");String userName = userService.getObj(queryWrapper, obj -> ((User) obj).getName()); // 调用 getObj 方法if (userName != null) { System.out.println("User name found: " + userName);} else { System.out.println("User name not found.");}
生成的 SQL:
SELECT * FROM user WHERE name = 'John Doe'
通过上述示例,我们可以看到 get
系列方法是如何在 Service 层进行查询操作的,以及它们对应的 SQL 语句。这些方法提供了灵活的数据查询方式,可以根据不同的条件进行查询操作。
list
// 查询所有List<T> list();// 查询列表List<T> list(Wrapper<T> queryWrapper);// 查询(根据ID 批量查询)Collection<T> listByIds(Collection<? extends Serializable> idList);// 查询(根据 columnMap 条件)Collection<T> listByMap(Map<String, Object> columnMap);// 查询所有列表List<Map<String, Object>> listMaps();// 查询列表List<Map<String, Object>> listMaps(Wrapper<T> queryWrapper);// 查询全部记录List<Object> listObjs();// 查询全部记录<V> List<V> listObjs(Function<? super Object, V> mapper);// 根据 Wrapper 条件,查询全部记录List<Object> listObjs(Wrapper<T> queryWrapper);// 根据 Wrapper 条件,查询全部记录<V> List<V> listObjs(Wrapper<T> queryWrapper, Function<? super Object, V> mapper);
功能描述: 查询符合条件的记录。
返回值: 查询结果,可能是实体对象、Map 对象或其他类型。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
Wrapper<T> | queryWrapper | 实体对象封装操作类 QueryWrapper |
Collection<? extends Serializable> | idList | 主键 ID 列表 |
Map<String, Object> | columnMap | 表字段 map 对象 |
Function<? super Object, V> | mapper | 转换函数 |
示例(list):
// 查询所有用户List<User> users = userService.list(); // 调用 list 方法for (User user : users) { System.out.println("User: " + user);}
生成的 SQL:
SELECT * FROM user
示例(list QueryWrapper 形式):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);List<User> users = userService.list(queryWrapper); // 调用 list 方法for (User user : users) { System.out.println("User: " + user);}
生成的 SQL:
SELECT * FROM user WHERE age > 25
示例(listByIds):
// 假设有一组 ID 列表,批量查询用户List<Integer> ids = Arrays.asList(1, 2, 3);Collection<User> users = userService.listByIds(ids); // 调用 listByIds 方法for (User user : users) { System.out.println("User: " + user);}
生成的 SQL:
SELECT * FROM user WHERE id IN (1, 2, 3)
示例(listByMap):
// 假设有一个 columnMap,设置查询条件为 age = 30Map<String, Object> columnMap = new HashMap<>();columnMap.put("age", 30);Collection<User> users = userService.listByMap(columnMap); // 调用 listByMap 方法for (User user : users) { System.out.println("User: " + user);}
生成的 SQL:
SELECT * FROM user WHERE age = 30
示例(listMaps):
// 查询所有用户,并将结果映射为 MapList<Map<String, Object>> userMaps = userService.listMaps(); // 调用 listMaps 方法for (Map<String, Object> userMap : userMaps) { System.out.println("User Map: " + userMap);}
生成的 SQL:
SELECT * FROM user
示例(listMaps QueryWrapper 形式):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,并将结果映射为 MapQueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);List<Map<String, Object>> userMaps = userService.listMaps(queryWrapper); // 调用 listMaps 方法for (Map<String, Object> userMap : userMaps) { System.out.println("User Map: " + userMap);}
生成的 SQL:
SELECT * FROM user WHERE age > 25
示例(listObjs):
// 查询所有用户,并将结果转换为 String 列表List<String> userNames = userService.listObjs(obj -> ((User) obj).getName()); // 调用 listObjs 方法for (String userName : userNames) { System.out.println("User Name: " + userName);}
生成的 SQL:
SELECT * FROM user
示例(listObjs QueryWrapper 形式):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,并将结果转换为 String 列表QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);List<String> userNames = userService.listObjs(queryWrapper, obj -> ((User) obj).getName()); // 调用 listObjs 方法for (String userName : userNames) { System.out.println("User Name: " + userName);}
生成的 SQL:
SELECT * FROM user WHERE age > 25
通过上述示例,我们可以看到 list
系列方法是如何在 Service 层进行查询操作的,以及它们对应的 SQL 语句。这些方法提供了灵活的数据查询方式,可以根据不同的条件进行查询操作。
page
// 无条件分页查询IPage<T> page(IPage<T> page);// 条件分页查询IPage<T> page(IPage<T> page, Wrapper<T> queryWrapper);// 无条件分页查询IPage<Map<String, Object>> pageMaps(IPage<T> page);// 条件分页查询IPage<Map<String, Object>> pageMaps(IPage<T> page, Wrapper<T> queryWrapper);
功能描述: 分页查询符合条件的记录。
返回值: 分页查询结果,包含记录列表和总记录数。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
IPage<T> | page | 翻页对象 |
Wrapper<T> | queryWrapper | 实体对象封装操作类 QueryWrapper |
示例(page):
// 假设要进行无条件的分页查询,每页显示10条记录,查询第1页IPage<User> page = new Page<>(1, 10);IPage<User> userPage = userService.page(page); // 调用 page 方法List<User> userList = userPage.getRecords();long total = userPage.getTotal();System.out.println("Total users: " + total);for (User user : userList) { System.out.println("User: " + user);}
生成的 SQL:
SELECT * FROM user LIMIT 10 OFFSET 0
示例(page QueryWrapper 形式):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,进行有条件的分页查询IPage<User> page = new Page<>(1, 10);QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);IPage<User> userPage = userService.page(page, queryWrapper); // 调用 page 方法List<User> userList = userPage.getRecords();long total = userPage.getTotal();System.out.println("Total users (age > 25): " + total);for (User user : userList) { System.out.println("User: " + user);}
生成的 SQL:
SELECT * FROM user WHERE age > 25 LIMIT 10 OFFSET 0
示例(pageMaps):
// 假设要进行无条件的分页查询,并将结果映射为 Map,每页显示10条记录,查询第1页IPage<Map<String, Object>> page = new Page<>(1, 10);IPage<Map<String, Object>> userPageMaps = userService.pageMaps(page); // 调用 pageMaps 方法List<Map<String, Object>> userMapList = userPageMaps.getRecords();long total = userPageMaps.getTotal();System.out.println("Total users: " + total);for (Map<String, Object> userMap : userMapList) { System.out.println("User Map: " + userMap);}
生成的 SQL:
SELECT * FROM user LIMIT 10 OFFSET 0
示例(pageMaps QueryWrapper 形式):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,进行有条件的分页查询,并将结果映射为 MapIPage<Map<String, Object>> page = new Page<>(1, 10);QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);IPage<Map<String, Object>> userPageMaps = userService.pageMaps(page, queryWrapper); // 调用 pageMaps 方法List<Map<String, Object>> userMapList = userPageMaps.getRecords();long total = userPageMaps.getTotal();System.out.println("Total users (age > 25): " + total);for (Map<String, Object> userMap : userMapList) { System.out.println("User Map: " + userMap);}
生成的 SQL:
SELECT * FROM user WHERE age > 25 LIMIT 10 OFFSET 0
通过上述示例,我们可以看到 page
系列方法是如何在 Service 层进行分页查询操作的,以及它们对应的 SQL 语句。这些方法提供了灵活的数据查询方式,可以根据不同的条件进行分页查询操作。
count
// 查询总记录数int count();// 根据 Wrapper 条件,查询总记录数int count(Wrapper<T> queryWrapper);
//自3.4.3.2开始,返回值修改为long// 查询总记录数long count();// 根据 Wrapper 条件,查询总记录数long count(Wrapper<T> queryWrapper);
功能描述: 查询符合条件的记录总数。
返回值: 符合条件的记录总数。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
Wrapper<T> | queryWrapper | 实体对象封装操作类 QueryWrapper |
示例(count):
// 查询用户表中的总记录数int totalUsers = userService.count(); // 调用 count 方法System.out.println("Total users: " + totalUsers);
生成的 SQL:
SELECT COUNT(*) FROM user
示例(count QueryWrapper 形式):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,查询满足条件的用户总数QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);int totalUsers = userService.count(queryWrapper); // 调用 count 方法System.out.println("Total users (age > 25): " + totalUsers);
生成的 SQL:
SELECT COUNT(*) FROM user WHERE age > 25
通过上述示例,我们可以看到 count
方法是如何在 Service 层进行记录数统计操作的,以及它们对应的 SQL 语句。这些方法提供了灵活的数据统计方式,可以根据不同的条件进行记录数统计。
Mapper Interface
BaseMapper 是 Mybatis-Plus 提供的一个通用 Mapper 接口,它封装了一系列常用的数据库操作方法,包括增、删、改、查等。通过继承 BaseMapper,开发者可以快速地对数据库进行操作,而无需编写繁琐的 SQL 语句。
insert
// 插入一条记录int insert(T entity);
功能描述: 插入一条记录。
返回值: int,表示插入操作影响的行数,通常为 1,表示插入成功。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
T | entity | 实体对象 |
示例(insert):
User user = new User();user.setName("John Doe");user.setEmail("john.doe@example.com");int rows = userMapper.insert(user); // 调用 insert 方法if (rows > 0) { System.out.println("User inserted successfully.");} else { System.out.println("Failed to insert user.");}
生成的 SQL:
INSERT INTO user (name, email) VALUES (?, ?)
通过上述示例,我们可以看到 insert
方法是如何在 Mapper 层进行插入操作的,以及它对应的 SQL 语句。这个方法简化了插入操作的实现,使得开发者无需手动编写 SQL 语句。
delete
// 根据 entity 条件,删除记录int delete(@Param(Constants.WRAPPER) Wrapper<T> wrapper);// 删除(根据ID 批量删除)int deleteBatchIds(@Param(Constants.COLLECTION) Collection<? extends Serializable> idList);// 根据 ID 删除int deleteById(Serializable id);// 根据 columnMap 条件,删除记录int deleteByMap(@Param(Constants.COLUMN_MAP) Map<String, Object> columnMap);
功能描述: 删除符合条件的记录。
返回值: int,表示删除操作影响的行数,通常为 1,表示删除成功。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
Wrapper<T> | wrapper | 实体对象封装操作类(可以为 null) |
Collection<? extends Serializable> | idList | 主键 ID 列表(不能为 null 以及 empty) |
Serializable | id | 主键 ID |
Map<String, Object> | columnMap | 表字段 map 对象 |
示例(delete):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,删除满足条件的用户QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);int rows = userMapper.delete(queryWrapper); // 调用 delete 方法if (rows > 0) { System.out.println("Users deleted successfully.");} else { System.out.println("No users deleted.");}
生成的 SQL:
DELETE FROM user WHERE age > 25
示例(deleteBatchIds):
// 假设有一组 ID 列表,批量删除用户List<Integer> ids = Arrays.asList(1, 2, 3);int rows = userMapper.deleteBatchIds(ids); // 调用 deleteBatchIds 方法if (rows > 0) { System.out.println("Users deleted successfully.");} else { System.out.println("No users deleted.");}
生成的 SQL:
DELETE FROM user WHERE id IN (1, 2, 3)
示例(deleteById):
// 根据 ID 删除单个用户int userId = 1;int rows = userMapper.deleteById(userId); // 调用 deleteById 方法if (rows > 0) { System.out.println("User deleted successfully.");} else { System.out.println("No user deleted.");}
生成的 SQL:
DELETE FROM user WHERE id = 1
示例(deleteByMap):
// 假设有一个 columnMap,设置查询条件为 age = 30,删除满足条件的用户Map<String, Object> columnMap = new HashMap<>();columnMap.put("age", 30);int rows = userMapper.deleteByMap(columnMap); // 调用 deleteByMap 方法if (rows > 0) { System.out.println("Users deleted successfully.");} else { System.out.println("No users deleted.");}
生成的 SQL:
DELETE FROM user WHERE age = 30
通过上述示例,我们可以看到 delete
系列方法是如何在 Mapper 层进行删除操作的,以及它们对应的 SQL 语句。这些方法提供了灵活的数据删除方式,可以根据不同的条件进行删除操作。
update
// 根据 whereWrapper 条件,更新记录int update(@Param(Constants.ENTITY) T updateEntity, @Param(Constants.WRAPPER) Wrapper<T> whereWrapper);// 根据 ID 修改int updateById(@Param(Constants.ENTITY) T entity);
功能描述: 更新符合条件的记录。
返回值: int,表示更新操作影响的行数,通常为 1,表示更新成功。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
T | entity | 实体对象 (set 条件值,可为 null) |
Wrapper<T> | updateWrapper | 实体对象封装操作类(可以为 null,里面的 entity 用于生成 where 语句) |
示例(update):
// 假设有一个 UpdateWrapper 对象,设置查询条件为 age > 25,更新满足条件的用户的邮箱UpdateWrapper<User> updateWrapper = new UpdateWrapper<>();updateWrapper.gt("age", 25);User updateUser = new User();updateUser.setEmail("new.email@example.com");int rows = userMapper.update(updateUser, updateWrapper); // 调用 update 方法if (rows > 0) { System.out.println("Users updated successfully.");} else { System.out.println("No users updated.");}
生成的 SQL:
UPDATE user SET email = ? WHERE age > 25
示例(updateById):
// 假设要更新 ID 为 1 的用户的邮箱User updateUser = new User();updateUser.setId(1);updateUser.setEmail("new.email@example.com");int rows = userMapper.updateById(updateUser); // 调用 updateById 方法if (rows > 0) { System.out.println("User updated successfully.");} else { System.out.println("No user updated.");}
生成的 SQL:
UPDATE user SET email = ? WHERE id = 1
通过上述示例,我们可以看到 update
系列方法是如何在 Mapper 层进行更新操作的,以及它们对应的 SQL 语句。这些方法提供了灵活的数据更新方式,可以根据不同的条件进行更新操作。
select
// 根据 ID 查询T selectById(Serializable id);// 根据 entity 条件,查询一条记录T selectOne(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);
// 查询(根据ID 批量查询)List<T> selectBatchIds(@Param(Constants.COLLECTION) Collection<? extends Serializable> idList);// 根据 entity 条件,查询全部记录List<T> selectList(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);// 查询(根据 columnMap 条件)List<T> selectByMap(@Param(Constants.COLUMN_MAP) Map<String, Object> columnMap);// 根据 Wrapper 条件,查询全部记录List<Map<String, Object>> selectMaps(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);// 根据 Wrapper 条件,查询全部记录。注意: 只返回第一个字段的值List<Object> selectObjs(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);
// 根据 entity 条件,查询全部记录(并翻页)IPage<T> selectPage(IPage<T> page, @Param(Constants.WRAPPER) Wrapper<T> queryWrapper);// 根据 Wrapper 条件,查询全部记录(并翻页)IPage<Map<String, Object>> selectMapsPage(IPage<T> page, @Param(Constants.WRAPPER) Wrapper<T> queryWrapper);// 根据 Wrapper 条件,查询总记录数Integer selectCount(@Param(Constants.WRAPPER) Wrapper<T> queryWrapper);
功能描述: 查询符合条件的记录。
返回值: 查询结果,可能是实体对象、Map 对象或其他类型。
参数说明:
类型 | 参数名 | 描述 |
---|---|---|
Serializable | id | 主键 ID |
Wrapper<T> | queryWrapper | 实体对象封装操作类(可以为 null) |
Collection<? extends Serializable> | idList | 主键 ID 列表(不能为 null 以及 empty) |
Map<String, Object> | columnMap | 表字段 map 对象 |
IPage<T> | page | 分页查询条件(可以为 RowBounds.DEFAULT) |
示例(selectById):
// 根据 ID 查询单个用户int userId = 1;User user = userMapper.selectById(userId); // 调用 selectById 方法System.out.println("User: " + user);
生成的 SQL:
SELECT * FROM user WHERE id = 1
示例(selectOne):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,查询一条满足条件的用户QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);User user = userMapper.selectOne(queryWrapper); // 调用 selectOne 方法System.out.println("User: " + user);
生成的 SQL:
SELECT * FROM user WHERE age > 25
示例(selectBatchIds):
// 假设有一组 ID 列表,批量查询用户List<Integer> ids = Arrays.asList(1, 2, 3);List<User> users = userMapper.selectBatchIds(ids); // 调用 selectBatchIds 方法for (User u : users) { System.out.println("User: " + u);}
生成的 SQL:
SELECT * FROM user WHERE id IN (1, 2, 3)
示例(selectList):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,查询所有满足条件的用户QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);List<User> users = userMapper.selectList(queryWrapper); // 调用 selectList 方法for (User u : users) { System.out.println("User: " + u);}
生成的 SQL:
SELECT * FROM user WHERE age > 25
示例(selectByMap):
// 假设有一个 columnMap,设置查询条件为 age > 30,查询满足条件的用户Map<String, Object> columnMap = new HashMap<>();columnMap.put("age", 30);List<User> users = userMapper.selectByMap(columnMap); // 调用 selectByMap 方法for (User u : users) { System.out.println("User: " + u);}
生成的 SQL:
SELECT * FROM user WHERE age > 30
示例(selectMaps):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,查询所有满足条件的用户,并将结果映射为 MapQueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);List<Map<String, Object>> userMaps = userMapper.selectMaps(queryWrapper); // 调用 selectMaps 方法for (Map<String, Object> userMap : userMaps) { System.out.println("User Map: " + userMap);}
生成的 SQL:
SELECT * FROM user WHERE age > 25
示例(selectObjs):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,查询所有满足条件的用户,但只返回每个记录的第一个字段的值QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);List<Object> userIds = userMapper.selectObjs(queryWrapper); // 调用 selectObjs 方法for (Object userId : userIds) { System.out.println("User ID: " + userId);}
生成的 SQL:
SELECT id FROM user WHERE age > 25
示例(selectPage):
// 假设要进行分页查询,每页显示10条记录,查询第1页,查询条件为 age > 25IPage<User> page = new Page<>(1, 10);QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);IPage<User> userPage = userMapper.selectPage(page, queryWrapper); // 调用 selectPage 方法List<User> userList = userPage.getRecords();long total = userPage.getTotal();System.out.println("Total users (age > 25): " + total);for (User user : userList) { System.out.println("User: " + user);}
生成的 SQL:
SELECT * FROM user WHERE age > 25 LIMIT 10 OFFSET 0
示例(selectMapsPage):
// 假设要进行分页查询,每页显示10条记录,查询第1页,查询条件为 age > 25,并将结果映射为 MapIPage<Map<String, Object>> = new Page<>(1, 10);QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);IPage<Map<String, Object>> userPageMaps = userMapper.selectMapsPage(page, queryWrapper); // 调用 selectMapsPage 方法List<Map<String, Object>> userMapList = userPageMaps.getRecords();long total = userPageMaps.getTotal();System.out.println("Total users (age > 25): " + total);for (Map<String, Object> userMap : userMapList) { System.out.println("User Map: " + userMap);}
生成的 SQL:
SELECT * FROM user WHERE age > 25 LIMIT 10 OFFSET 0
示例(selectCount):
// 假设有一个 QueryWrapper 对象,设置查询条件为 age > 25,查询总记录数QueryWrapper<User> queryWrapper = new QueryWrapper<>();queryWrapper.gt("age", 25);Integer totalUsers = userMapper.selectCount(queryWrapper); // 调用 selectCount 方法System.out.println("Total users (age > 25): " + totalUsers);
生成的 SQL:
SELECT COUNT(*) FROM user WHERE age > 25
通过上述示例,我们可以看到 select
系列方法是如何在 Mapper 层进行查询操作的,以及它们对应的 SQL 语句。这些方法提供了灵活的数据查询方式,可以根据不同的条件进行查询操作,包括单条记录查询、批量查询、条件查询、分页查询等。
Mapper 层选装件
选装件是 Mybatis-Plus 提供的一些扩展方法,它们位于 com.baomidou.mybatisplus.extension.injector.methods
包下。这些方法需要配合Sql 注入器使用,以扩展 Mapper 接口的功能。
使用这些选装件前,需要确保已经正确配置了 Sql 注入器。更多使用案例和详细信息,可以参考官方案例和源码注释。
选装件说明
alwaysUpdateSomeColumnById
int alwaysUpdateSomeColumnById(T entity);
源码:alwaysUpdateSomeColumnById
功能:这个方法用于在更新操作时,无论实体对象的某些字段是否有变化,都会强制更新这些字段。这在某些业务场景下非常有用,比如更新时间戳字段,确保每次更新操作都会更新该字段。
使用场景:当你需要在每次更新记录时,都更新某些特定的字段(如更新时间、版本号等),即使这些字段在实体对象中没有变化。
insertBatchSomeColumn
int insertBatchSomeColumn(List<T> entityList);
源码:insertBatchSomeColumn
功能:这个方法用于批量插入实体对象,但只插入实体对象中指定的某些字段。这在需要批量插入数据,但又不希望插入所有字段时非常有用。
使用场景:当你需要批量插入数据,并且希望只插入实体对象中的部分字段,以提高插入效率或保护敏感数据。
logicDeleteByIdWithFill
int logicDeleteByIdWithFill(T entity);
源码:logicDeleteByIdWithFill
功能:这个方法用于逻辑删除记录,并填充实体对象中的某些字段。逻辑删除意味着不是真正从数据库中删除记录,而是通过更新某个字段(如 deleted
字段)来标记记录已被删除。
使用场景:当你需要实现逻辑删除功能,并且希望在删除操作时自动填充实体对象中的某些字段(如删除时间、删除人等)。
使用提示
- 在使用这些选装件之前,确保你的项目中已经正确配置了 Sql 注入器。
- 这些方法通常需要在 Mapper 接口中显式声明,以便 Mybatis-Plus 能够识别并生成相应的 SQL 语句。
- 每个选装件都有其特定的使用场景,根据业务需求选择合适的方法。
- 在实际使用中,可能需要结合实体对象的注解(如
@TableField
、@TableLogic
等)来实现更复杂的功能。
通过使用这些选装件,可以进一步扩展 Mybatis-Plus 的功能,满足更多样化的业务需求。
Chain
Chain 是 Mybatis-Plus 提供的一种链式编程风格,它允许开发者以更加简洁和直观的方式编写数据库操作代码。Chain 分为 query
和 update
两大类,分别用于查询和更新操作。每类又分为普通链式和 lambda 链式两种风格,其中 lambda 链式提供了类型安全的查询条件构造,但不支持 Kotlin。
使用步骤
query
提供链式查询操作,可以连续调用方法来构建查询条件。
// 链式查询 普通QueryChainWrapper<T> query();// 链式查询 lambda 式。注意:不支持 KotlinLambdaQueryChainWrapper<T> lambdaQuery();
示例:
// 普通链式查询示例query().eq("name", "John").list(); // 查询 name 为 "John" 的所有记录
// lambda 链式查询示例lambdaQuery().eq(User::getAge, 30).one(); // 查询年龄为 30 的单条记录
update
提供链式更新操作,可以连续调用方法来构建更新条件。
// 链式更改 普通UpdateChainWrapper<T> update();// 链式更改 lambda 式。注意:不支持 KotlinLambdaUpdateChainWrapper<T> lambdaUpdate();
示例:
// 普通链式更新示例update().set("status", "inactive").eq("name", "John").update(); // 将 name 为 "John" 的记录 status 更新为 "inactive"
// lambda 链式更新示例User updateUser = new User();updateUser.setEmail("new.email@example.com");lambdaUpdate().set(User::getEmail, updateUser.getEmail()).eq(User::getId, 1).update(); // 更新 ID 为 1 的用户的邮箱
使用提示
- 链式操作通过返回
QueryChainWrapper
或UpdateChainWrapper
的实例,允许开发者连续调用方法来构建查询或更新条件。 - lambda 链式操作提供了类型安全的查询条件构造,通过方法引用
Entity::getId
等方式,避免了字符串硬编码,提高了代码的可读性和安全性。 - 在使用链式操作时,注意链式方法的调用顺序,通常是先设置条件,然后执行查询或更新操作。
- 链式操作支持多种条件构造方法,如
eq
、ne
、gt
、lt
、like
等,可以根据实际需求选择合适的方法。 - 链式操作返回的结果可以是单条记录、多条记录、总记录数等,具体取决于最后调用的方法。
通过使用 Chain,开发者可以更加高效地编写数据库操作代码,同时保持代码的清晰和可维护性。
ActiveRecord
ActiveRecord 模式是一种设计模式,它允许实体类直接与数据库进行交互,实体类既是领域模型又是数据访问对象。在 Mybatis-Plus 中,实体类只需继承 Model
类即可获得强大的 CRUD 操作能力。
使用步骤
继承 Model 类
import com.baomidou.mybatisplus.extension.activerecord.Model;
public class User extends Model<User> { // 实体类的字段定义... private Long id; private String name; private Integer age; // ... 其他字段和 getter/setter 方法}
调用 CRUD 方法
// 创建新用户并插入数据库User user = new User();user.setName("John Doe");user.setAge(30);boolean isInserted = user.insert(); // 返回值表示操作是否成功
// 查询所有用户List<User> allUsers = user.selectAll();
// 根据 ID 更新用户信息user.setId(1L);user.setName("Updated Name");boolean isUpdated = user.updateById(); // 返回值表示操作是否成功
// 根据 ID 删除用户boolean isDeleted = user.deleteById(); // 返回值表示操作是否成功
使用提示
- 在 ActiveRecord 模式下,实体类可以直接调用
insert
、selectAll
、updateById
、deleteById
等方法进行数据库操作。 - 实体类继承
Model
类后,会自动获得一系列数据库操作方法,无需手动编写 SQL 语句。 - 实体类中的字段需要与数据库表中的列对应,通常通过注解(如
@TableField
、@TableId
等)来指定字段与列的映射关系。 - 在进行更新或删除操作时,通常需要先查询出实体对象,然后修改其属性,最后调用更新或删除方法。
- 插入和更新操作通常会返回一个布尔值,表示操作是否成功。
- 查询操作会返回相应的查询结果,如单个实体对象或实体对象列表。
通过使用 ActiveRecord 模式,开发者可以更加简洁地编写数据库操作代码,同时保持代码的清晰和可维护性。这种模式尤其适合于简单的 CRUD 操作,可以大大减少重复代码的编写。
SimpleQuery
SimpleQuery 是 Mybatis-Plus 提供的一个工具类,它对 selectList
查询后的结果进行了封装,使其可以通过 Stream
流的方式进行处理,从而简化了 API 的调用。
SimpleQuery 的一个特点是它的 peeks
参数,这是一个可变参数,类型为 Consumer...
,意味着你可以连续添加多个操作,这些操作会在查询结果被处理时依次执行。
SimpleQuery 的使用方式可以参考官方测试用例。
使用步骤
引入 SimpleQuery 工具类
import com.baomidou.mybatisplus.core.toolkit.support.SFunction;import com.baomidou.mybatisplus.core.toolkit.support.SerializedLambda;import com.baomidou.mybatisplus.core.toolkit.support.SimpleQuery;
使用 SimpleQuery 进行查询
// 假设有一个 User 实体类和对应的 BaseMapperList<Long> ids = SimpleQuery.list( Wrappers.lambdaQuery(User.class), // 使用 lambda 查询构建器 User::getId, // 提取的字段,这里是 User 的 id System.out::println, // 第一个 peek 操作,打印每个用户 user -> userNames.add(user.getName()) // 第二个 peek 操作,将每个用户的名字添加到 userNames 列表中);
使用提示
- SimpleQuery 工具类提供了一种简洁的方式来处理查询结果,它允许你在查询结果上应用多个操作,这些操作会按照添加的顺序依次执行。
- 在使用 SimpleQuery 时,你需要提供一个查询构建器(如
Wrappers.lambdaQuery()
),一个用于提取结果的字段(如User::getId
),以及一个或多个Consumer
类型的peek
操作。 peek
操作可以用于执行任何副作用操作,如打印日志、更新缓存、发送通知等,而不会影响查询结果本身。- SimpleQuery 返回的结果是一个列表,包含了所有查询到的实体对象,这些对象已经应用了所有的
peek
操作。 - 通过使用 SimpleQuery,你可以将查询和结果处理逻辑分离,使代码更加清晰和易于维护。
通过使用 SimpleQuery 工具类,开发者可以更加高效地处理查询结果,同时保持代码的简洁性和可读性。这种工具类尤其适合于需要对查询结果进行复杂处理的场景。
功能详解
keyMap
SimpleQuery 的 keyMap
方法提供了一种便捷的方式来查询数据库,并将查询结果封装成一个 Map
,其中实体的某个属性作为键(key),实体本身作为值(value)。这个方法还支持在处理查询结果时执行额外的副作用操作,如打印日志或更新缓存。
方法签名
// 查询表内记录,封装返回为 Map<属性,实体>Map<A, E> keyMap(LambdaQueryWrapper<E> wrapper, SFunction<E, A> sFunction, Consumer<E>... peeks);
// 查询表内记录,封装返回为 Map<属性,实体>,考虑了并行流的情况Map<A, E> keyMap(LambdaQueryWrapper<E> wrapper, SFunction<E, A> sFunction, boolean isParallel, Consumer<E>... peeks);
参数说明
类型 | 参数名 | 描述 |
---|---|---|
E | entity | 实体对象类型,即查询结果的实体类型。 |
A | attribute | 实体属性类型,也是返回的 Map 中键(key)的类型。 |
LambdaQueryWrapper<E> | wrapper | 支持 lambda 表达式的条件构造器,用于构建查询条件。 |
SFunction<E, A> | sFunction | 实体中属性的 getter 方法引用,用于确定 Map 中键(key)的值。 |
boolean | isParallel | 如果设置为 true ,则底层使用并行流执行查询,可以提高处理大量数据时的效率。 |
Consumer<E>… | peeks | 可变参数,用于指定在处理查询结果时执行的额外操作,如打印日志、更新缓存等。 |
使用示例
// 假设有一个 User 实体类和对应的 BaseMapperLambdaQueryWrapper<User> queryWrapper = new LambdaQueryWrapper<>();queryWrapper.eq(User::getStatus, "active"); // 查询状态为 "active" 的用户
// 使用 keyMap 方法查询并封装结果Map<String, User> userMap = SimpleQuery.keyMap( queryWrapper, // 查询条件构造器 User::getUsername, // 使用用户名作为键 user -> System.out.println("Processing user: " + user.getUsername()) // 打印处理的用户名);
// 遍历结果for (Map.Entry<String, User> entry : userMap.entrySet()) { System.out.println("Key: " + entry.getKey() + ", Value: " + entry.getValue());}
使用提示
keyMap
方法适用于需要根据实体的某个属性快速查找实体的场景。- 通过
sFunction
参数,你可以指定任何实体属性作为Map
的键,这使得查询结果的访问更加直观和高效。 peeks
参数允许你在处理查询结果时执行额外的副作用操作,这些操作不会影响最终的Map
结果。- 当处理大量数据时,可以考虑将
isParallel
参数设置为true
以启用并行流,从而提高查询效率。
通过使用 SimpleQuery 的 keyMap
方法,开发者可以更加高效地处理查询结果,并将其封装成易于使用的数据结构,同时还可以执行额外的副作用操作,使代码更加简洁和灵活。
map
SimpleQuery 的 map
方法提供了一种便捷的方式来查询数据库,并将查询结果封装成一个 Map
,其中实体的某个属性作为键(key),另一个属性作为值(value)。这个方法还支持在处理查询结果时执行额外的副作用操作,如打印日志或更新缓存。
方法签名
// 查询表内记录,封装返回为 Map<属性,属性>Map<A, P> map(LambdaQueryWrapper<E> wrapper, SFunction<E, A> keyFunc, SFunction<E, P> valueFunc, Consumer<E>... peeks);
// 查询表内记录,封装返回为 Map<属性,属性>,考虑了并行流的情况Map<A, P> map(LambdaQueryWrapper<E> wrapper, SFunction<E, A> keyFunc, SFunction<E, P> valueFunc, boolean isParallel, Consumer<E>... peeks);
参数说明
类型 | 参数名 | 描述 |
---|---|---|
E | entity | 实体对象类型,即查询结果的实体类型。 |
A | attribute | 实体属性类型,作为返回的 Map 中键(key)的类型。 |
P | attribute | 实体属性类型,作为返回的 Map 中值(value)的类型。 |
LambdaQueryWrapper<E> | wrapper | 支持 lambda 表达式的条件构造器,用于构建查询条件。 |
SFunction<E, A> | keyFunc | 实体中属性的 getter 方法引用,用于确定 Map 中键(key)的值。 |
SFunction<E, P> | valueFunc | 实体中属性的 getter 方法引用,用于确定 Map 中值(value)的值。 |
boolean | isParallel | 如果设置为 true ,则底层使用并行流执行查询,可以提高处理大量数据时的效率。 |
Consumer<E>… | peeks | 可变参数,用于指定在处理查询结果时执行的额外操作,如打印日志、更新缓存等。 |
使用示例
// 假设有一个 User 实体类和对应的 BaseMapperLambdaQueryWrapper<User> queryWrapper = new LambdaQueryWrapper<>();queryWrapper.eq(User::getStatus, "active"); // 查询状态为 "active" 的用户
// 使用 map 方法查询并封装结果Map<String, Integer> userMap = SimpleQuery.map( queryWrapper, // 查询条件构造器 User::getUsername, // 使用用户名作为键 User::getAge, // 使用年龄作为值 user -> System.out.println("Processing user: " + user.getUsername()) // 打印处理的用户名);
// 遍历结果for (Map.Entry<String, Integer> entry : userMap.entrySet()) { System.out.println("Username: " + entry.getKey() + ", Age: " + entry.getValue());}
使用提示
map
方法适用于需要根据实体的某个属性快速查找另一个属性的场景。- 通过
keyFunc
和valueFunc
参数,你可以指定任何实体属性作为Map
的键和值,这使得查询结果的访问更加直观和高效。 peeks
参数允许你在处理查询结果时执行额外的副作用操作,这些操作不会影响最终的Map
结果。- 当处理大量数据时,可以考虑将
isParallel
参数设置为true
以启用并行流,从而提高查询效率。
通过使用 SimpleQuery 的 map
方法,开发者可以更加高效地处理查询结果,并将其封装成易于使用的数据结构,同时还可以执行额外的副作用操作,使代码更加简洁和灵活。
group
SimpleQuery 的 group
方法提供了一种便捷的方式来查询数据库,并将查询结果按照实体的某个属性进行分组,封装成一个 Map
。这个方法还支持在处理查询结果时执行额外的副作用操作,如打印日志或更新缓存。此外,它还允许你使用 Collector
对分组后的集合进行进一步的处理。
方法签名
// 查询表内记录,封装返回为 Map<属性,List<实体>>Map<K, List<T>> group(LambdaQueryWrapper<T> wrapper, SFunction<T, K> sFunction, Consumer<T>... peeks);
// 查询表内记录,封装返回为 Map<属性,List<实体>>,考虑了并行流的情况Map<K, List<T>> group(LambdaQueryWrapper<T> wrapper, SFunction<T, K> sFunction, boolean isParallel, Consumer<T>... peeks);
// 查询表内记录,封装返回为 Map<属性,分组后对集合进行的下游收集器>M group(LambdaQueryWrapper<T> wrapper, SFunction<T, K> sFunction, Collector<? super T, A, D> downstream, Consumer<T>... peeks);
// 查询表内记录,封装返回为 Map<属性,分组后对集合进行的下游收集器>,考虑了并行流的情况M group(LambdaQueryWrapper<T> wrapper, SFunction<T, K> sFunction, Collector<? super T, A, D> downstream, boolean isParallel, Consumer<T>... peeks);
参数说明
类型 | 参数名 | 描述 |
---|---|---|
T | entity | 实体对象类型,即查询结果的实体类型。 |
K | attribute | 实体属性类型,作为返回的 Map 中键(key)的类型。 |
D | - | 下游收集器返回类型,作为 Map 中值(value)的类型。 |
A | - | 下游操作中间类型,用于 Collector 的中间结果。 |
M | - | 最终结束返回的 Map<K, D> 类型。 |
LambdaQueryWrapper<T> | wrapper | 支持 lambda 表达式的条件构造器,用于构建查询条件。 |
SFunction<T, K> | sFunction | 分组依据,实体中属性的 getter 方法引用,用于确定 Map 中键(key)的值。 |
Collector<T, A, D> | downstream | 下游收集器,用于对分组后的集合进行进一步的处理。 |
boolean | isParallel | 如果设置为 true ,则底层使用并行流执行查询,可以提高处理大量数据时的效率。 |
Consumer<T>… | peeks | 可变参数,用于指定在处理查询结果时执行的额外操作,如打印日志、更新缓存等。 |
使用示例
// 假设有一个 User 实体类和对应的 BaseMapperLambdaQueryWrapper<User> queryWrapper = new LambdaQueryWrapper<>();queryWrapper.eq(User::getStatus, "active"); // 查询状态为 "active" 的用户
// 使用 group 方法查询并封装结果,按照用户名分组Map<String, List<User>> userGroup = SimpleQuery.group( queryWrapper, // 查询条件构造器 User::getUsername, // 使用用户名作为分组键 user -> System.out.println("Processing user: " + user.getUsername()) // 打印处理的用户名);
// 遍历结果for (Map.Entry<String, List<User>> entry : userGroup.entrySet()) { System.out.println("Username: " + entry.getKey()); for (User user : entry.getValue()) { System.out.println(" - User: " + user); }}
使用提示
group
方法适用于需要根据实体的某个属性对查询结果进行分组的场景。- 通过
sFunction
参数,你可以指定任何实体属性作为分组的依据,这使得查询结果的组织更加灵活。 downstream
参数允许你使用Collector
对分组后的集合进行进一步的处理,如计数、求和、平均值等。peeks
参数允许你在处理查询结果时执行额外的副作用操作,这些操作不会影响最终的Map
结果。- 当处理大量数据时,可以考虑将
isParallel
参数设置为true
以启用并行流,从而提高查询效率。
通过使用 SimpleQuery 的 group
方法,开发者可以更加高效地处理查询结果,并将其按照特定属性进行分组,同时还可以执行额外的副作用操作,使代码更加简洁和灵活。
list
SimpleQuery 的 list
方法提供了一种便捷的方式来查询数据库,并将查询结果封装成一个 List
,其中列表的元素是实体的某个属性。这个方法还支持在处理查询结果时执行额外的副作用操作,如打印日志或更新缓存。
方法签名
// 查询表内记录,封装返回为 List<属性>List<A> list(LambdaQueryWrapper<E> wrapper, SFunction<E, A> sFunction, Consumer<E>... peeks);
// 查询表内记录,封装返回为 List<属性>,考虑了并行流的情况List<A> list(LambdaQueryWrapper<E> wrapper, SFunction<E, A> sFunction, boolean isParallel, Consumer<E>... peeks);
参数说明
类型 | 参数名 | 描述 |
---|---|---|
E | entity | 实体对象类型,即查询结果的实体类型。 |
A | attribute | 实体属性类型,作为返回的 List 中元素的类型。 |
LambdaQueryWrapper<E> | wrapper | 支持 lambda 表达式的条件构造器,用于构建查询条件。 |
SFunction<E, A> | sFunction | 实体中属性的 getter 方法引用,用于确定 List 中元素的值。 |
boolean | isParallel | 如果设置为 true ,则底层使用并行流执行查询,可以提高处理大量数据时的效率。 |
Consumer<E>… | peeks | 可变参数,用于指定在处理查询结果时执行的额外操作,如打印日志、更新缓存等。 |
使用示例
// 假设有一个 User 实体类和对应的 BaseMapperLambdaQueryWrapper<User> queryWrapper = new LambdaQueryWrapper<>();queryWrapper.eq(User::getStatus, "active"); // 查询状态为 "active" 的用户
// 使用 list 方法查询并封装结果,提取所有用户的用户名List<String> userNames = SimpleQuery.list( queryWrapper, // 查询条件构造器 User::getUsername, // 提取用户名作为列表元素 user -> System.out.println("Processing user: " + user.getUsername()) // 打印处理的用户名);
// 遍历结果for (String username : userNames) { System.out.println("Username: " + username);}
使用提示
list
方法适用于需要根据实体的某个属性快速获取一个列表的场景。- 通过
sFunction
参数,你可以指定任何实体属性作为List
的元素,这使得查询结果的访问更加直观和高效。 peeks
参数允许你在处理查询结果时执行额外的副作用操作,这些操作不会影响最终的List
结果。- 当处理大量数据时,可以考虑将
isParallel
参数设置为true
以启用并行流,从而提高查询效率。
通过使用 SimpleQuery 的 list
方法,开发者可以更加高效地处理查询结果,并将其封装成易于使用的数据结构,同时还可以执行额外的副作用操作,使代码更加简洁和灵活。
Db Kit
Db Kit 是 Mybatis-Plus 提供的一个工具类,它允许开发者通过静态调用的方式执行 CRUD 操作,从而避免了在 Spring 环境下可能出现的 Service 循环注入问题,简化了代码,提升了开发效率。
Db Kit 的完整使用方式可以参考官方测试用例。
使用示例
// 假设有一个 User 实体类和对应的 BaseMapper
// 根据 id 查询单个实体User user = Db.getById(1L, User.class);
// 根据 id 查询多个实体List<User> userList = Db.listByIds(Arrays.asList(1L, 2L, 3L), User.class);
// 根据条件构造器查询LambdaQueryWrapper<User> queryWrapper = Wrappers.lambdaQuery(User.class) .eq(User::getStatus, "active");List<User> activeUsers = Db.list(queryWrapper);
// 插入新实体User newUser = new User();newUser.setUsername("newUser");newUser.setAge(25);boolean isInserted = Db.insert(newUser);
// 根据 id 更新实体User updateUser = new User();updateUser.setId(1L);updateUser.setUsername("updatedUser");boolean isUpdated = Db.updateById(updateUser);
// 根据条件构造器更新LambdaUpdateWrapper<User> updateWrapper = Wrappers.lambdaUpdate(User.class) .set(User::getAge, 30) .eq(User::getUsername, "updatedUser");boolean isUpdatedByWrapper = Db.update(null, updateWrapper);
// 根据 id 删除实体boolean isDeleted = Db.removeById(1L);
// 根据条件构造器删除LambdaDeleteWrapper<User> deleteWrapper = Wrappers.lambdaDelete(User.class) .eq(User::getStatus, "inactive");boolean isDeletedByWrapper = Db.remove(deleteWrapper);
// 批量插入List<User> batchUsers = Arrays.asList( new User("user1", 20), new User("user2", 22), new User("user3", 24));boolean isBatchInserted = Db.saveBatch(batchUsers);
// 批量更新List<User> batchUpdateUsers = Arrays.asList( new User(1L, "user1", 21), new User(2L, "user2", 23), new User(3L, "user3", 25));boolean isBatchUpdated = Db.updateBatchById(batchUpdateUsers);
使用提示
- Db Kit 提供了一系列静态方法,可以直接调用进行数据库操作,无需通过 Service 层,简化了代码结构。
- 在使用 Db Kit 时,确保传入的参数正确,特别是当使用 Wrapper 时,需要指定实体类或实体对象。
- 对于批量操作,如批量插入或更新,建议使用 Db Kit 提供的批量方法,以提高效率。
- 避免在循环中频繁调用 Db Kit 的方法,这可能会导致性能问题。
通过使用 Db Kit,开发者可以更加高效地执行数据库操作,同时保持代码的简洁性和可读性。这种工具类尤其适合于简单的 CRUD 操作,可以大大减少重复代码的编写。