Mybatis-Flex之增、删、改
方法全解
(1) INSERT
BaseMapper 的接口提供了 insert 和 insertBatch 方法,用于新增数据;
- insert(entity):插入实体类数据,不忽略 null 值。
- insertSelective(entity):插入实体类数据,但是忽略 null 的数据,只对有值的内容进行插入。这样的好处是数据库已经配置了一些默认值,这些默认值才会生效。
- insert(entity, ignoreNulls):插入实体类数据。
- insertWithPk(entity):插入带有主键的实体类,不忽略 null 值。
- insertSelectiveWithPk(entity):插入带有主键的实体类,忽略 null 值。
- insertWithPk(entity, ignoreNulls):带有主键的插入,此时实体类不会经过主键生成器生成主键。
- insertBatch(entities):批量插入实体类数据,只会根据第一条数据来构建插入的字段内容。
- insertBatch(entities, size):批量插入实体类数据,按 size 切分。
- insertOrUpdate(entity):插入或者更新,若主键有值,则更新,若没有主键值,则插入,插入或者更新都不会忽略 null 值。
- insertOrUpdateSelective(entity):插入或者更新,若主键有值,则更新,若没有主键值,则插入,插入或者更新都会忽略 null 值。
- insertOrUpdate(entity, ignoreNulls):插入或者更新,若主键有值,则更新,若没有主键值,则插入。
① insert
/**
* insert(entity):插入实体类数据,不忽略 null 值。
* insert(entity, ignoreNulls):插入实体类数据。
*/
@Test
public void testInsert() {
/**
* 默认不忽略null值
* INSERT INTO `tb_account`(`user_name`, `age`, `birthday`) VALUES (?, ?, ?)
*/
int row = accountMapper.insert(new Account().setUserName(null).setBirthday(new Date()).setAge(25));
Assertions.assertEquals(row, 1);
/**
* ignoreNulls true:忽略null , false:不忽略null
* INSERT INTO `tb_account`(`user_name`) VALUES (?)
*/
int row2 = accountMapper.insert(new Account().setUserName("ly3").setBirthday(null).setAge(null), true);
Assertions.assertEquals(row2, 1);
}
② insertSelective
/**
* insertSelective(entity):插入实体类数据,但是忽略 null 的数据,只对有值的内容进行插入。这样的好处是数据库已经配置了一些默认值,这些默认值才会生效。
*/
@Test
public void testInsertSelective() {
/**
* INSERT INTO `tb_account`(`user_name`) VALUES (?)
*/
int row = accountMapper.insertSelective(new Account().setUserName("陈远航").setAge(null));
Assertions.assertEquals(row, 1);
}
③ insertWithPk
/**
* insertWithPk(entity):插入带有主键的实体类,不忽略 null 值。
*/
@Test
public void testInsertWithPk() {
/**
* INSERT INTO `tb_account`(`id`, `user_name`, `age`, `birthday`) VALUES (?, ?, ?, ?)
*/
int row = accountMapper.insertWithPk(new Account().setUserName("廖楷瑞").setId(5L).setBirthday(null));
Assertions.assertEquals(row, 1);
}
④ insertBatch
/**
* insertBatch(entities):批量插入实体类数据,只会根据第一条数据来构建插入的字段内容。
* insertBatch(entities, size):批量插入实体类数据,按 size 切分。
*/
@Test
public void testInsertBatch() {
List<Account> accounts = new ArrayList<>(10);
for (int i = 0; i < 10; i++) {
Account account = new Account().setUserName("ly" + i).setBirthday(new Date()).setAge(20 + i);
accounts.add(account);
}
/**
* 批量插入,可以指定每次插入的数据大小size
* size=2 : INSERT INTO `tb_account`(`user_name`, `age`, `birthday`) VALUES (?, ?, ?), (?, ?, ?)
* size=3 : INSERT INTO `tb_account`(`user_name`, `age`, `birthday`) VALUES (?, ?, ?), (?, ?, ?), (?, ?, ?)
* ......
*/
int rows = accountMapper.insertBatch(accounts, 2);
System.out.println("rows = " + rows);
}
⑤ insertOrUpdate
/**
* insertOrUpdate(entity):插入或者更新,若主键有值,则更新,若没有主键值,则插入,插入或者更新都不会忽略 null 值。
* insertOrUpdateSelective(entity):插入或者更新,若主键有值,则更新,若没有主键值,则插入,插入或者更新都会忽略 null 值。
* insertOrUpdate(entity, ignoreNulls):插入或者更新,若主键有值,则更新,若没有主键值,则插入。
*/
@Test
public void testInsertOrUpdate() {
Account account = new Account().setUserName("ly-update2").setId(3L).setBirthday(new Date()).setAge(21);
/**
* UPDATE `tb_account` SET `user_name` = ? , `age` = ? , `birthday` = ? WHERE `id` = ?
*/
int row = accountMapper.insertOrUpdate(account);
Assertions.assertEquals(row, 0, 1);
account = new Account().setUserName("ly-update2").setBirthday(null).setAge(21);
/**
* INSERT INTO `tb_account`(`user_name`, `age`) VALUES (?, ?)
*/
int row2 = accountMapper.insertOrUpdateSelective(account);
Assertions.assertEquals(row2, 0, 1);
}
(2) DELETE
BaseMapper 的接口提供了 deleteById、deleteBatchByIds、deleteByMap、deleteByQuery 方法,用于删除数据;
- deleteById(id):根据主键删除数据。如果是多个主键的情况下,需要传入数组,例如:new Integer[]{100,101}。
- deleteBatchByIds(ids):根据多个主键批量删除数据。
- deleteBatchByIds(ids, size):根据多个主键批量删除数据。
- deleteByMap(whereConditions):根据 Map 构建的条件来删除数据。
- deleteByCondition(whereConditions):根据查询条件来删除数据。
- deleteByQuery(queryWrapper):根据查询条件来删除数据。
① deleteById
/**
* deleteById(id):根据主键删除数据。
* ??? 如果是多个主键的情况下,需要传入数组,例如:new Integer[]{100,101}。 ??? 怀疑态度
*/
@Test
public void testDeleteById() {
/**
* DELETE FROM `tb_account` WHERE `id` = ?
*/
int row = accountMapper.deleteById(9L);
Assertions.assertTrue(row > 0);
}
② deleteBatchByIds
/**
* deleteBatchByIds(ids):根据多个主键批量删除数据。
* deleteBatchByIds(ids, size):根据多个主键批量删除数据。
*/
@Test
public void testDeleteBatchByIds() {
List<Integer> ids = List.of(5, 6, 7, 8);
/**
* DELETE FROM `tb_account` WHERE `id` = ? OR `id` = ? OR `id` = ? OR `id` = ?
*/
int rows = accountMapper.deleteBatchByIds(ids);
Assertions.assertTrue(rows > 0);
/**
* 分批删除
* size=2 : DELETE FROM `tb_account` WHERE `id` = ? OR `id` = ?
*/
int rows2 = accountMapper.deleteBatchByIds(ids, 2);
Assertions.assertTrue(rows2 > 0);
}
③ deleteByMap
/**
* deleteByMap(whereConditions):根据 Map 构建的条件来删除数据。
*/
@Test
public void testDeleteByMap() {
/**
* DELETE FROM `tb_account` WHERE `tb_account`.`age` = ?
*/
int rows = accountMapper.deleteByMap(Map.of("age", 25));
Assertions.assertTrue(rows > 0);
}
④ deleteByCondition
/**
* deleteByCondition(whereConditions):根据查询条件来删除数据。
*/
@Test
public void testDeleteByCondition() {
QueryCondition condition = QueryCondition.createEmpty().and("age = 27");
/**
* DELETE FROM `tb_account` WHERE age = 27
*/
int rows = accountMapper.deleteByCondition(condition);
Assertions.assertTrue(rows > 0);
/**
* DELETE FROM `tb_account` WHERE `id` > ?
*/
int rows2 = accountMapper.deleteByCondition(ACCOUNT.ID.gt(35));
Assertions.assertTrue(rows2 > 0);
}
⑤ deleteByQuery
/**
* deleteByQuery(queryWrapper):根据查询条件来删除数据。
*/
@Test
public void testDeleteByQuery() {
/**
* DELETE FROM `tb_account` WHERE `age` >= ?
*/
QueryWrapper wrapper = QueryWrapper.create().where(ACCOUNT.AGE.ge(32));
int rows = accountMapper.deleteByQuery(wrapper);
Assertions.assertTrue(rows > 0);
}
(3) UPDATE
BaseMapper 的接口提供了 update、updateByMap、updateByQuery 方法,用于更新数据;
- update(entity):根据主键来更新数据,若实体类属性数据为 null,该属性不会新到数据库。
- update(entity, ignoreNulls):根据主键来更新数据到数据库。
- updateByMap(entity, whereConditions):根据 Map 构建的条件来更新数据。
- updateByMap(entity, ignoreNulls, whereConditions):根据 Map 构建的条件来更新数据。
- updateByCondition(entity, whereConditions):根据查询条件来更新数据。
- updateByCondition(entity, ignoreNulls, whereConditions):根据查询条件来更新数据。
- updateByQuery(entity, queryWrapper):根据查询条件来更新数据。
- updateByQuery(entity, ignoreNulls, queryWrapper):根据查询条件来更新数据。
① update
@Test
public void testUpdate() {
Account account = new Account().setId(5L)
.setAge(39)
.setUserName("测试修改")
.setBirthday(new Date(2023, Calendar.SEPTEMBER, 6, 12, 12, 12));
/**
* UPDATE `tb_account` SET `user_name` = ? , `age` = ? , `birthday` = ? WHERE `id` = ?
*/
int rows = accountMapper.update(account);
Assertions.assertTrue(rows > 0);
}
@Test
public void testUpdateIgnoreNulls() {
Account account = new Account().setId(6L)
.setAge(null)
.setUserName(null)
.setBirthday(new Date(2023, Calendar.SEPTEMBER, 6, 12, 12, 12));
/**
* 不忽略null值
* UPDATE `tb_account` SET `user_name` = ? , `age` = ? , `birthday` = ? WHERE `id` = ?
*/
int rows = accountMapper.update(account, false);
System.out.println("rows = " + rows);
}
② updateByMap
@Test
public void testUpdateByMap() {
Account account = new Account()
.setId(7L) // 不生效
.setUserName("updateByMap")
.setAge(24)
.setBirthday(null);
// 注意:这样更新实体类的id是不生效的
Map<String, Object> whereCondition = Map.of("id", 13);
/**
* 忽略null
* UPDATE `tb_account` SET `user_name` = ? , `age` = ? WHERE `id` = ?
*/
accountMapper.updateByMap(account, whereCondition);
/**
* 不忽略null
* UPDATE `tb_account` SET `user_name` = ? , `age` = ? , `birthday` = ? WHERE `id` = ?
*/
accountMapper.updateByMap(account, false, whereCondition);
}
③ updateByCondition
/**
* updateByCondition(entity, whereConditions):根据查询条件来更新数据。
* updateByCondition(entity, ignoreNulls, whereConditions):根据查询条件来更新数据。
*/
@Test
public void testUpdateByCondition() {
Account account = new Account()
.setId(8L)
.setUserName("updateByCondition")
.setBirthday(DateUtil.toDate(LocalDateTime.now()));
QueryCondition condition = QueryCondition.create(new QueryColumn("id"),
SqlConsts.EQUALS, 8);
/**
* 忽略null
* UPDATE `tb_account` SET `user_name` = ? , `birthday` = ? WHERE `id` = ?
*/
accountMapper.updateByCondition(account, condition);
/**
* 不忽略null
* UPDATE `tb_account` SET `user_name` = ? , `age` = ? , `birthday` = ? WHERE `id` = ?
*/
accountMapper.updateByCondition(account, false, condition);
}
④ updateByQuery
/**
* updateByQuery(entity, queryWrapper):根据查询条件来更新数据。
* updateByQuery(entity, ignoreNulls, queryWrapper):根据查询条件来更新数据。
*/
@Test
public void testUpdateByQuery() {
Account account = new Account().setUserName("updateByQuery");
/**
* UPDATE `tb_account` SET `user_name` = ? WHERE `id` = ?
*/
accountMapper.updateByQuery(account,
QueryWrapper.create().where(ACCOUNT.ID.eq(9L)));
}
⑤ UpdateEntity部分字段更新
@Test
public void testUpdateEntity1() {
Account account = UpdateEntity.of(Account.class, 10L);
/**
* 官方说明:通过 UpdateEntity 创建的对象,只会更新调用了 setter 方法的字段,若不调用 setter 方法,不管这个对象里的属性的值是什么,都不会更新到数据库。
*/
account.setAge(66)
.setUserName("UpdateEntity")
.setBirthday(null);
accountMapper.update(account);
}
@Test
public void testUpdateEntity2() {
Account account = new Account()
.setId(10L)
.setUserName("UpdateEntity2");
UpdateWrapper wrapper = UpdateWrapper.of(account);
// wrapper.set(ACCOUNT.AGE, ACCOUNT.AGE.add(1));
wrapper.setRaw("age", "age + 1");
accountMapper.update(account);
}
@Test
public void testUpdateEntity3() {
Account account = new Account()
.setId(10L)
.setUserName("UpdateEntity2");
UpdateWrapper wrapper = UpdateWrapper.of(account);
// wrapper.set(ACCOUNT.AGE, ACCOUNT.AGE.add(1));
wrapper.setRaw(ACCOUNT.AGE, "select * from t_account where id = 3");
// accountMapper.updateByCondition(account, wrapper);
}
⑥ UpdateChain
@Test
public void testUpdateChain() {
/**
* UPDATE `tb_account` SET `birthday` = ? , `age` = age + 1 WHERE `age` = ?
*/
UpdateChain.of(Account.class)
.set(Account::getBirthday, new Date())
.setRaw(Account::getAge, "age + 1")
.where(ACCOUNT.AGE.eq(11)).update();
}
set() 和 setRaw() 的区别
在 Row、UpdateWrapper、UpdateChain 中,都提供了 set() 和 setRaw() 两个方法用于设置数据。 那么,他们有什么区别呢?
- set() 方法用于设置参数数据。
- setRaw() 用于设置 SQL 拼接数据。
Mybatis-Flex之增、删、改的更多相关文章
- C# ADO.NET (sql语句连接方式)(增,删,改)
using System; using System.Collections.Generic; using System.Linq; using System.Web; using System.We ...
- 好用的SQL TVP~~独家赠送[增-删-改-查]的例子
以前总是追求新东西,发现基础才是最重要的,今年主要的目标是精通SQL查询和SQL性能优化. 本系列主要是针对T-SQL的总结. [T-SQL基础]01.单表查询-几道sql查询题 [T-SQL基础] ...
- iOS FMDB的使用(增,删,改,查,sqlite存取图片)
iOS FMDB的使用(增,删,改,查,sqlite存取图片) 在上一篇博客我对sqlite的基本使用进行了详细介绍... 但是在实际开发中原生使用的频率是很少的... 这篇博客我将会较全面的介绍FM ...
- iOS sqlite3 的基本使用(增 删 改 查)
iOS sqlite3 的基本使用(增 删 改 查) 这篇博客不会讲述太多sql语言,目的重在实现sqlite3的一些基本操作. 例:增 删 改 查 如果想了解更多的sql语言可以利用强大的互联网. ...
- ADO.NET 增 删 改 查
ADO.NET:(数据访问技术)就是将C#和MSSQL连接起来的一个纽带 可以通过ADO.NET将内存中的临时数据写入到数据库中 也可以将数据库中的数据提取到内存中供程序调用 ADO.NET所有数据访 ...
- MVC EF 增 删 改 查
using System;using System.Collections.Generic;using System.Linq;using System.Web;//using System.Data ...
- 第18课-数据库开发及ado.net 连接数据库.增.删.改向表中插入数据并且返回自动编号.SQLDataReade读取数据
第18课-数据库开发及ado.net 连接数据库.增.删.改向表中插入数据并且返回自动编号.SQLDataReade读取数据 ADO.NET 为什么要学习? 我们要搭建一个平台(Web/Winform ...
- django ajax增 删 改 查
具于django ajax实现增 删 改 查功能 代码示例: 代码: urls.py from django.conf.urls import url from django.contrib impo ...
- StringBuilder修改字符串内容,增,删,改,插
package seday01;/** * 字符串不变对象特性只针对字符串重用,并没有考虑修改操作的性能.因此String不适合频繁修改内容. * 若有频繁修改操作,使用StringBuilder来完 ...
- python基础中的四大天王-增-删-改-查
列表-list-[] 输入内存储存容器 发生改变通常直接变化,让我们看看下面列子 增---默认在最后添加 #append()--括号中可以是数字,可以是字符串,可以是元祖,可以是集合,可以是字典 #l ...
随机推荐
- AI绘画:StableDiffusion炼丹Lora攻略-实战萌宠图片生成
写在前面的话 近期在小红书发现了许多极其可爱.美观的萌宠图片,对这些美妙的图像深深着迷 于是想着看看利用AI绘画StableDiffusion以下简称(SD)做出来. 以下是详细实操的全过程,包括所有 ...
- Programming abstractions in C阅读笔记:p132-p137
<Programming Abstractions In C>学习第53天,p132-p137,3.2小节"strings"总结如下: 一.技术总结 3.2小节介绍了字 ...
- Vue【原创】日历组件Calendar
最近项目中封装了一个日历组件,用于节假日管理,支持输入默认选中的日期,选择管理日期. 效果图: calendar组件: 1 <template> 2 <div class=" ...
- Java开发面试--Redis专区
1. 什么是Redis?它的主要特点是什么? 答: Redis是一个开源的.基于内存的高性能键值对存储系统.它主要用于缓存.数据存储和消息队列等场景. 高性能:Redis将数据存储在内存中,并采用单线 ...
- SpingCloud:Gateway+Nginx+Stomp+Minio构建聊天室并进行文件传输
注:本人使用阿里云服务器(安装mino)+本地虚拟机(安装nginx)进行,理论上完全在本地进行也可以. 1.前期准备: 1.将本地虚拟机设置为静态ip且能ping通外网,参考网址:https://w ...
- Chrome 手机端网页如何使用开发者模式
chrome 手机端网页如何调试 在Chrome手机端,你可以使用Chrome开发者工具来调试网页.下面是一些步骤: 首先,确保你的手机已经开启开发者模式.打开USB调试功能或可以通过USB连接或无线 ...
- Nexus搭建maven仓库并使用
一.基本介绍 参考:https://www.hangge.com/blog/cache/detail_2844.html https://blog.csdn.net/zhuguanbo/article ...
- 怎么搭建web组态
web组态是指通过可视化拖拽组件的方式,低代码搭建监控大屏.web页面.物联网各行业的数据以及监控场景,每个行业的业务不同,需要展示的页面也不同.组态快速搭建页面的优势,能更好的满足不同定制化监控页面 ...
- Python基础——字符编码、文件处理
文章目录 字符编码 一 引入 二 知识储备 2.1 三大核心硬件 2.2 文本编辑器读取文件内容的流程 2.3 python解释器执行文件的流程 2.4 总结 三.字符编码介绍 3.1 什么是字符编码 ...
- Informix 4gl错误代码信息和更正
(一)Informix信息和更正 出版日期:6 1996 年 年 1 11 月 0 成功. 操作成功.当 SQL 语句成功地执行时,数据库服务器把这个 SQLCODE 值返回给应用程序. 100 没有 ...