[JavaWeb]【八】web后端开发-Mybatis
目录
一 介绍
二 Mybatis的入门
2.1 快速入门
2.1.1 准备SpringBoot工程
2.1.2 创建数据库mybatis以及对应库表user
2.1.3 创建User实体类
2.1.4 配置application.properties数据库连接信息
2.1.5 编写sql语句(注解方式)
2.1.6 测试运行
2.1.7 配置SQL提示
2.2 JDBC介绍(了解)
2.2.1 JDBC 介绍
2.2.2 jdbc与Mybatis对比
2.3 数据库连接池(了解)
2.3.1 概念
2.3.2 mybatis切换Druid(德鲁伊)连接池
2.3.3 总结
2.4 lombok
三 Mybatis的基础操作
3.1 准备工作
3.1.1 数据脚本在mybatis表执行脚本
3.1.2 创建一个springboot项目
3.1.3 application.properties配置
3.1.4 创建对应实体类Emp
3.1.5 准备Mapper接口EmpMapper
3.2 日志输出
3.2.1 性能高
3.2.2 更安全
3.2.3 总结 使用#
3.3 删除
3.3.1 EmpMapper接口添加 删除方法
3.3.2 新增测试方法
3.4 新增
3.4.1 EmpMapper接口添加 新增方法
3.4.2 新增测试方法
3.4.3 主键返回
3.4.4 总结
3.5 更新
3.5.1 EmpMapper接口添加 更新方法
3.5.2 新增测试方法
3.6 查询
3.6.1 EmpMapper接口添加 查询方法
3.6.2 新增测试方法
3.6.3 数据封装
3.6.3.1 方案一 (不推荐):当数据库字段与实体类字段不一致时取别名
3.6.3.2 方案二(不推荐) :通过@Results, @Result注解手动映射封装
3.6.3.3 方案三(推荐):开启mybatis的驼峰命名自动映射开关
3.7 查询(条件查询)
3.7.1 EmpMapper接口添加 条件查询方法
3.7.2 新增测试方法
3.7.3 使用concat解决使用'%$name}%'问题
四 XML映射文件
4.1 XML映射规范
4.1.1 第一步:
4.1.2 第二步:编辑
4.1.3 第三步
4.1.4 验证
4.2 mybatisx插件
4.3 总结
五 Mybatis的动态SQL
5.1
5.1.1 优化EmpMapper.xml
5.1.2 案例
5.1.2.1 优化EmpMapper 新增一个方法update2
5.1.2.2 EmpMpapper.xml新增一个update2的sql
5.1.2.3 新增测试方法testUpdate2测试
编辑5.1.3 总结
5.2
5.2.1 优化EmpMapper 新增一个方法deleteByIds
5.2.2 EmpMpapper.xml新增一个deleteByIds的sql
5.2.3 新增测试方法testDeleteByids
5.2.4 总结
5.3
5.3.1 EmpMpapper.xml新增sql 标签优化list2 include标签
5.3.2 执行测试方法testList2
5.4 总结
前言:Mybatis数据持久层,进行数据库操作,增删改查 ,动态sql
一 介绍

二 Mybatis的入门
2.1 快速入门
案例

2.1.1 准备SpringBoot工程


2.1.2 创建数据库mybatis以及对应库表user
create database mybatis;
create table user(id int unsigned primary key auto_increment comment 'ID',name varchar(100) comment '姓名',age tinyint unsigned comment '年龄',gender tinyint unsigned comment '性别, 1:男, 2:女',phone varchar(11) comment '手机号'
) comment '用户表';insert into user(id, name, age, gender, phone) VALUES (null,'白眉鹰王',55,'1','18800000000');
insert into user(id, name, age, gender, phone) VALUES (null,'金毛狮王',45,'1','18800000001');
insert into user(id, name, age, gender, phone) VALUES (null,'青翼蝠王',38,'1','18800000002');
insert into user(id, name, age, gender, phone) VALUES (null,'紫衫龙王',42,'2','18800000003');
insert into user(id, name, age, gender, phone) VALUES (null,'光明左使',37,'1','18800000004');
insert into user(id, name, age, gender, phone) VALUES (null,'光明右使',48,'1','18800000005');
2.1.3 创建User实体类

package com.runa.pojo;public class User {private Integer id;private String name;private Short age;private Short gender;private String phone;public User() {}public User(Integer id, String name, Short age, Short gender, String phone) {this.id = id;this.name = name;this.age = age;this.gender = gender;this.phone = phone;}public Integer getId() {return id;}public void setId(Integer id) {this.id = id;}public String getName() {return name;}public void setName(String name) {this.name = name;}public Short getAge() {return age;}public void setAge(Short age) {this.age = age;}public Short getGender() {return gender;}public void setGender(Short gender) {this.gender = gender;}public String getPhone() {return phone;}public void setPhone(String phone) {this.phone = phone;}@Overridepublic String toString() {return "User{" +"id=" + id +", name='" + name + '\'' +", age=" + age +", gender=" + gender +", phone='" + phone + '\'' +'}';}
}
2.1.4 配置application.properties数据库连接信息
# 配置数据库连接信息
#驱动类名称
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
#数据库连接的url
spring.datasource.url=jdbc:mysql://localhost:3306/mybatis
#连接数据库的用户名
spring.datasource.username=root
#连接数据库的密码
spring.datasource.password=1234
package com.runa.pojo;public class User {private Integer id;private String name;private Short age;private Short gender;private String phone;public User(Integer id, String name, Short age, Short gender, String phone) {this.id = id;this.name = name;this.age = age;this.gender = gender;this.phone = phone;}public User() {}public Integer getId() {return id;}public void setId(Integer id) {this.id = id;}public String getName() {return name;}public void setName(String name) {this.name = name;}public Short getAge() {return age;}public void setAge(Short age) {this.age = age;}public Short getGender() {return gender;}public void setGender(Short gender) {this.gender = gender;}public String getPhone() {return phone;}public void setPhone(String phone) {this.phone = phone;}@Overridepublic String toString() {return "User{" +"id=" + id +", name='" + name + '\'' +", age=" + age +", gender=" + gender +", phone='" + phone + '\'' +'}';}
}
2.1.5 编写sql语句(注解方式)

package com.runa.mapper;import com.runa.pojo.User;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Select;import java.util.List;@Mapper // 运行时,会自动生成该接口的实现类对象(代理对象),并且将改对象交给IOC容器管理
public interface UserMapper {// 查询全部用户信息@Select("select * from user")public List<User> list();
}
2.1.6 测试运行
package com.runa;import com.runa.mapper.UserMapper;
import com.runa.pojo.User;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;import java.util.List;@SpringBootTest
class SpringbootMybatisQuickstartApplicationTests {@Autowired // 注入private UserMapper userMapper;@Testpublic void testListUser() {List<User> userList = userMapper.list();userList.stream().forEach(user -> {System.out.println(user);});}// @Test
// void contextLoads() {
// }}


2.1.7 配置SQL提示


设置好,还不行的话(删除其他数据库连接,刷新数据库连接),重启IEDA
2.2 JDBC介绍(了解)
2.2.1 JDBC 介绍

@Testpublic void testJdbc() throws Exception {//1 注册驱动Class.forName("com.mysql.cj.jdbc.Driver");// 2 获取连接对象String url = "jdbc:mysql://localhost:3306/mybatis";String username = "root";String password = "runa#2050";Connection connection = DriverManager.getConnection(url, username, password);// 3 获取执行sql的对象statement,执行sql 返回结果String sql = "select * from user";Statement statement = null;statement = connection.createStatement();ResultSet resultSet = null;resultSet = statement.executeQuery(sql);// 4 封装结果数据List<User> userList = new ArrayList<>();while (resultSet.next()) {int id = resultSet.getInt("id");String name = resultSet.getString("name");short age = resultSet.getShort("age");short gender = resultSet.getShort("gender");String phone = resultSet.getString("phone");User user = new User(id, name, age, gender, phone);userList.add(user);}// 5 释放资源statement.close();connection.close();userList.stream().forEach(user -> {System.out.println(user);});}

2.2.2 jdbc与Mybatis对比

2.3 数据库连接池(了解)
2.3.1 概念


2.3.2 mybatis切换Druid(德鲁伊)连接池

我没有配置成功
2.3.3 总结

2.4 lombok


添加依赖
<dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId></dependency>
修改实体类User
package com.runa.pojo;import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;@Data
@NoArgsConstructor
@AllArgsConstructor
public class User {private Integer id;private String name;private Short age;private Short gender;private String phone;}
三 Mybatis的基础操作

3.1 准备工作

3.1.1 数据脚本在mybatis表执行脚本
-- 部门管理
create table dept(id int unsigned primary key auto_increment comment '主键ID',name varchar(10) not null unique comment '部门名称',create_time datetime not null comment '创建时间',update_time datetime not null comment '修改时间'
) comment '部门表';insert into dept (id, name, create_time, update_time) values(1,'学工部',now(),now()),(2,'教研部',now(),now()),(3,'咨询部',now(),now()), (4,'就业部',now(),now()),(5,'人事部',now(),now());-- 员工管理
create table emp (id int unsigned primary key auto_increment comment 'ID',username varchar(20) not null unique comment '用户名',password varchar(32) default '123456' comment '密码',name varchar(10) not null comment '姓名',gender tinyint unsigned not null comment '性别, 说明: 1 男, 2 女',image varchar(300) comment '图像',job tinyint unsigned comment '职位, 说明: 1 班主任,2 讲师, 3 学工主管, 4 教研主管, 5 咨询师',entrydate date comment '入职时间',dept_id int unsigned comment '部门ID',create_time datetime not null comment '创建时间',update_time datetime not null comment '修改时间'
) comment '员工表';INSERT INTO emp(id, username, password, name, gender, image, job, entrydate,dept_id, create_time, update_time) VALUES(1,'jinyong','123456','金庸',1,'1.jpg',4,'2000-01-01',2,now(),now()),(2,'zhangwuji','123456','张无忌',1,'2.jpg',2,'2015-01-01',2,now(),now()),(3,'yangxiao','123456','杨逍',1,'3.jpg',2,'2008-05-01',2,now(),now()),(4,'weiyixiao','123456','韦一笑',1,'4.jpg',2,'2007-01-01',2,now(),now()),(5,'changyuchun','123456','常遇春',1,'5.jpg',2,'2012-12-05',2,now(),now()),(6,'xiaozhao','123456','小昭',2,'6.jpg',3,'2013-09-05',1,now(),now()),(7,'jixiaofu','123456','纪晓芙',2,'7.jpg',1,'2005-08-01',1,now(),now()),(8,'zhouzhiruo','123456','周芷若',2,'8.jpg',1,'2014-11-09',1,now(),now()),(9,'dingminjun','123456','丁敏君',2,'9.jpg',1,'2011-03-11',1,now(),now()),(10,'zhaomin','123456','赵敏',2,'10.jpg',1,'2013-09-05',1,now(),now()),(11,'luzhangke','123456','鹿杖客',1,'11.jpg',5,'2007-02-01',3,now(),now()),(12,'hebiweng','123456','鹤笔翁',1,'12.jpg',5,'2008-08-18',3,now(),now()),(13,'fangdongbai','123456','方东白',1,'13.jpg',5,'2012-11-01',3,now(),now()),(14,'zhangsanfeng','123456','张三丰',1,'14.jpg',2,'2002-08-01',2,now(),now()),(15,'yulianzhou','123456','俞莲舟',1,'15.jpg',2,'2011-05-01',2,now(),now()),(16,'songyuanqiao','123456','宋远桥',1,'16.jpg',2,'2010-01-01',2,now(),now()),(17,'chenyouliang','123456','陈友谅',1,'17.jpg',NULL,'2015-03-21',NULL,now(),now());
3.1.2 创建一个springboot项目
引入起步依赖mybatis、mysql驱动、lombok
3.1.3 application.properties配置
指定mybatis输出日志的位置。输出控制台
# 配置数据库连接
# 驱动类名称
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
# 连接数据库的url
spring.datasource.url=jdbc:mysql://localhost:3306/mybatis
#连接数据库用户名
spring.datasource.username=root
# 连接数据库密码
spring.datasource.password=runa#2050# 指定mybatis输出日志的位置。输出控制台
mybatis.configuration.log-impl=org.apache.ibatis.logging.stdout.StdOutImpl
3.1.4 创建对应实体类Emp

package com.runa.pojo;import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.time.LocalDate;
import java.time.LocalDateTime;@Data
@NoArgsConstructor
@AllArgsConstructor
public class Emp {private Integer id;private String username;private String password;private String name;private Short gender;private String image;private Short job;private LocalDate entrydate;private Integer deptId;private LocalDateTime createTime;private LocalDateTime updateTime;
}
3.1.5 准备Mapper接口EmpMapper

package com.runa.mapper;import org.apache.ibatis.annotations.Mapper;@Mapper
public interface EmpMapper {
}
3.2 日志输出

3.2.1 性能高

3.2.2 更安全


3.2.3 总结 使用#

3.3 删除

3.3.1 EmpMapper接口添加 删除方法
package com.runa.mapper;import org.apache.ibatis.annotations.Delete;
import org.apache.ibatis.annotations.Mapper;@Mapper
public interface EmpMapper {// 根据id删除数据@Delete("delete from emp where id = #{id}")public void delete(Integer id);
}
3.3.2 新增测试方法
package com.runa;import com.runa.mapper.EmpMapper;
import com.runa.mapper.UserMapper;
import com.runa.pojo.User;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;import java.sql.*;
import java.util.ArrayList;
import java.util.List;@SpringBootTest
class SpringbootMybatisQuickstartApplicationTests {@Autowired //注入private EmpMapper empMapper;@Testpublic void testDelete(){empMapper.delete(17);}}
改造一下获取返回值
package com.runa.mapper;import org.apache.ibatis.annotations.Delete;
import org.apache.ibatis.annotations.Mapper;@Mapper
public interface EmpMapper {// 根据id删除数据
// @Delete("delete from emp where id = #{id}")
// public void delete(Integer id);// 根据id删除数据,并获取返回值@Delete("delete from emp where id = #{id}")public int delete(Integer id);
}
package com.runa;import com.runa.mapper.EmpMapper;
import com.runa.mapper.UserMapper;
import com.runa.pojo.User;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;import java.sql.*;
import java.util.ArrayList;
import java.util.List;@SpringBootTest
class SpringbootMybatisQuickstartApplicationTests {// @Autowired // 注入
// private UserMapper userMapper;@Autowired //注入private EmpMapper empMapper;// @Test
// public void testListUser() {
// List<User> userList = userMapper.list();
// userList.stream().forEach(user -> {
// System.out.println(user);
// });
// }// @Test
// public void testDelete(){
// empMapper.delete(17);
//
// }@Test // 获取返回值public void testDelete(){int id = empMapper.delete(16);System.out.println(id);}}
返回 1表示删除成功,0 是失败
3.4 新增

3.4.1 EmpMapper接口添加 新增方法
package com.runa.mapper;import com.runa.pojo.Emp;
import org.apache.ibatis.annotations.Delete;
import org.apache.ibatis.annotations.Insert;
import org.apache.ibatis.annotations.Mapper;@Mapper
public interface EmpMapper {// 根据id删除数据@Delete("delete from emp where id = #{id}")public void delete(Integer id);// 根据id删除数据,并获取返回值
// @Delete("delete from emp where id = #{id}")
// public int delete(Integer id);// 新增员工@Insert("insert into emp\n" +"(username, name, gender, image, job, entrydate,dept_id, create_time, update_time)" +" VALUES(#{username},#{name},#{gender},#{image},#{job},#{entrydate},#{deptId},#{createTime},#{updateTime})")public void insert(Emp emp);}
3.4.2 新增测试方法
package com.runa;import com.runa.mapper.EmpMapper;
import com.runa.mapper.UserMapper;
import com.runa.pojo.Emp;
import com.runa.pojo.User;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;import java.sql.*;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;@SpringBootTest
class SpringbootMybatisQuickstartApplicationTests {// @Autowired // 注入
// private UserMapper userMapper;@Autowired //注入private EmpMapper empMapper;// @Test
// public void testListUser() {
// List<User> userList = userMapper.list();
// userList.stream().forEach(user -> {
// System.out.println(user);
// });
// }@Testpublic void testDelete(){empMapper.delete(17);}// @Test // 获取返回值
// public void testDelete(){
// int id = empMapper.delete(16);
// System.out.println(id);
// }@Testpublic void testInsert(){// 构造员工对象Emp emp = new Emp();emp.setUsername("Bocai");emp.setName("菠菜");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setCreateTime(LocalDateTime.now());emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行新增员工的信息操作empMapper.insert(emp);}}
3.4.3 主键返回

3.4.4 总结

3.5 更新

3.5.1 EmpMapper接口添加 更新方法
package com.runa.mapper;import com.runa.pojo.Emp;
import org.apache.ibatis.annotations.*;@Mapper
public interface EmpMapper {// 根据id删除数据@Delete("delete from emp where id = #{id}")public void delete(Integer id);// 根据id删除数据,并获取返回值
// @Delete("delete from emp where id = #{id}")
// public int delete(Integer id);// 新增员工@Options(useGeneratedKeys = true, keyProperty = "id")@Insert("insert into emp" +"(username, name, gender, image, job, entrydate,dept_id, create_time, update_time)" +" VALUES(#{username},#{name},#{gender},#{image},#{job},#{entrydate},#{deptId},#{createTime},#{updateTime})")public void insert(Emp emp);// 更新员工信息@Update("update emp set username = #{username}, name = #{name}, gender = #{gender}, image = #{image}, " +"job = #{job}, entrydate = #{entrydate},dept_id = #{deptId}, update_time = #{updateTime} where id = #{id}")public void update(Emp emp);}
3.5.2 新增测试方法
package com.runa;import com.runa.mapper.EmpMapper;
import com.runa.mapper.UserMapper;
import com.runa.pojo.Emp;
import com.runa.pojo.User;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;import java.sql.*;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;@SpringBootTest
class SpringbootMybatisQuickstartApplicationTests {// @Autowired // 注入
// private UserMapper userMapper;@Autowired //注入private EmpMapper empMapper;// @Test
// public void testListUser() {
// List<User> userList = userMapper.list();
// userList.stream().forEach(user -> {
// System.out.println(user);
// });
// }@Testpublic void testDelete(){empMapper.delete(17);}// @Test // 获取返回值
// public void testDelete(){
// int id = empMapper.delete(16);
// System.out.println(id);
// }@Testpublic void testInsert(){// 构造员工对象Emp emp = new Emp();emp.setUsername("Bocai1");emp.setName("菠菜1");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setCreateTime(LocalDateTime.now());emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行新增员工的信息操作empMapper.insert(emp);System.out.println(emp.getId());}@Testpublic void testUpdate(){// 构造员工对象Emp emp = new Emp();emp.setId(19);emp.setUsername("Spring");emp.setName("春天的菠菜");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行更新员工的信息操作empMapper.update(emp);}}
3.6 查询

3.6.1 EmpMapper接口添加 查询方法
package com.runa.mapper;import com.runa.pojo.Emp;
import org.apache.ibatis.annotations.*;@Mapper
public interface EmpMapper {// 根据id删除数据@Delete("delete from emp where id = #{id}")public void delete(Integer id);// 根据id删除数据,并获取返回值
// @Delete("delete from emp where id = #{id}")
// public int delete(Integer id);// 新增员工@Options(useGeneratedKeys = true, keyProperty = "id")@Insert("insert into emp" +"(username, name, gender, image, job, entrydate,dept_id, create_time, update_time)" +" VALUES(#{username},#{name},#{gender},#{image},#{job},#{entrydate},#{deptId},#{createTime},#{updateTime})")public void insert(Emp emp);// 更新员工信息@Update("update emp set username = #{username}, name = #{name}, gender = #{gender}, image = #{image}, " +"job = #{job}, entrydate = #{entrydate},dept_id = #{deptId}, update_time = #{updateTime} where id = #{id}")public void update(Emp emp);// 根据ID查询员工@Select("select * from emp where id = #{id}")public Emp getById(Integer id);}
3.6.2 新增测试方法
package com.runa;import com.runa.mapper.EmpMapper;
import com.runa.mapper.UserMapper;
import com.runa.pojo.Emp;
import com.runa.pojo.User;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;import java.sql.*;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;@SpringBootTest
class SpringbootMybatisQuickstartApplicationTests {// @Autowired // 注入
// private UserMapper userMapper;@Autowired //注入private EmpMapper empMapper;// @Test
// public void testListUser() {
// List<User> userList = userMapper.list();
// userList.stream().forEach(user -> {
// System.out.println(user);
// });
// }@Testpublic void testDelete(){empMapper.delete(17);}// @Test // 获取返回值
// public void testDelete(){
// int id = empMapper.delete(16);
// System.out.println(id);
// }// 测试新增@Testpublic void testInsert(){// 构造员工对象Emp emp = new Emp();emp.setUsername("Bocai1");emp.setName("菠菜1");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setCreateTime(LocalDateTime.now());emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行新增员工的信息操作empMapper.insert(emp);System.out.println(emp.getId());}// 测试更新@Testpublic void testUpdate(){// 构造员工对象Emp emp = new Emp();emp.setId(19);emp.setUsername("Spring");emp.setName("春天的菠菜");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行更新员工的信息操作empMapper.update(emp);}// 根据员工ID查询员工@Testpublic void testGetById(){Emp emp = empMapper.getById(19);System.out.println(emp);}}
3.6.3 数据封装

3.6.3.1 方案一 (不推荐):当数据库字段与实体类字段不一致时取别名
修改Empmapper接口类
// 根据ID查询员工
// @Select("select * from emp where id = #{id}")
// public Emp getById(Integer id);// 根据ID查询员工,取别名方案@Select("select id,id, username, password, name, gender, image, job, entrydate, dept_id deptId, create_time createTime, update_time updateTime from emp where id = #{id}")public Emp getById(Integer id);

3.6.3.2 方案二(不推荐) :通过@Results, @Result注解手动映射封装
// 根据ID查询员工
// @Select("select * from emp where id = #{id}")
// public Emp getById(Integer id);// 根据ID查询员工,方案一:取别名方案
// @Select("select id,id, username, password, name, gender, image, job, entrydate, dept_id deptId, create_time createTime, update_time updateTime from emp where id = #{id}")
// public Emp getById(Integer id);// 根据ID查询员工 方案二:通过@Results, @Result注解手动映射封装@Results({@Result(column = "dept_id", property = "deptId"),@Result(column = "create_time", property = "createTime"),@Result(column = "update_time", property = "updateTime")})@Select("select * from emp where id = #{id}")public Emp getById(Integer id);

3.6.3.3 方案三(推荐):开启mybatis的驼峰命名自动映射开关
application.properties新增配置
# 配置数据库连接
# 驱动类名称
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
# 连接数据库的url
spring.datasource.url=jdbc:mysql://localhost:3306/mybatis
#连接数据库用户名
spring.datasource.username=root
# 连接数据库密码
spring.datasource.password=runa#2050# 指定mybatis输出日志的位置。输出控制台
mybatis.configuration.log-impl=org.apache.ibatis.logging.stdout.StdOutImpl# # 开启mybatis的驼峰命名自动映射开关
mybatis.configuration.map-underscore-to-camel-case=true

插曲:IDEA 的application.properties中文乱码,
配置前:
修改后:

3.7 查询(条件查询)


3.7.1 EmpMapper接口添加 条件查询方法
'%#{name}%' #{name} 不能出现在''里面所以改成$
package com.runa.mapper;import com.runa.pojo.Emp;
import org.apache.ibatis.annotations.*;import java.time.LocalDate;
import java.util.List;@Mapper
public interface EmpMapper {// 根据id删除数据@Delete("delete from emp where id = #{id}")public void delete(Integer id);// 根据id删除数据,并获取返回值
// @Delete("delete from emp where id = #{id}")
// public int delete(Integer id);// 新增员工@Options(useGeneratedKeys = true, keyProperty = "id")@Insert("insert into emp" +"(username, name, gender, image, job, entrydate,dept_id, create_time, update_time)" +" VALUES(#{username},#{name},#{gender},#{image},#{job},#{entrydate},#{deptId},#{createTime},#{updateTime})")public void insert(Emp emp);// 更新员工信息@Update("update emp set username = #{username}, name = #{name}, gender = #{gender}, image = #{image}, " +"job = #{job}, entrydate = #{entrydate},dept_id = #{deptId}, update_time = #{updateTime} where id = #{id}")public void update(Emp emp);// 根据ID查询员工@Select("select * from emp where id = #{id}")public Emp getById(Integer id);// 根据ID查询员工, (不推荐)方案一:取别名方案
// @Select("select id,id, username, password, name, gender, image, job, entrydate, dept_id deptId, create_time createTime, update_time updateTime from emp where id = #{id}")
// public Emp getById(Integer id);// 根据ID查询员工 (不推荐)方案二:通过@Results, @Result注解手动映射封装
// @Results({
// @Result(column = "dept_id", property = "deptId"),
// @Result(column = "create_time", property = "createTime"),
// @Result(column = "update_time", property = "updateTime")
// })
// @Select("select * from emp where id = #{id}")
// public Emp getById(Integer id);// 条件查询员工 '%#{name}%' #{name} 不能出现在''里面所以改成$@Select("select * from emp where name like '%${name}%'and gender = #{gender} and entrydate between #{begin} and #{end} order by update_time desc ")public List<Emp> list(String name, Short gender, LocalDate begin, LocalDate end);}
3.7.2 新增测试方法
package com.runa;import com.runa.mapper.EmpMapper;
import com.runa.mapper.UserMapper;
import com.runa.pojo.Emp;
import com.runa.pojo.User;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;import java.sql.*;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;@SpringBootTest
class SpringbootMybatisQuickstartApplicationTests {// @Autowired // 注入
// private UserMapper userMapper;@Autowired //注入private EmpMapper empMapper;// @Test
// public void testListUser() {
// List<User> userList = userMapper.list();
// userList.stream().forEach(user -> {
// System.out.println(user);
// });
// }@Testpublic void testDelete(){empMapper.delete(17);}// @Test // 获取返回值
// public void testDelete(){
// int id = empMapper.delete(16);
// System.out.println(id);
// }// 测试新增@Testpublic void testInsert(){// 构造员工对象Emp emp = new Emp();emp.setUsername("Bocai1");emp.setName("菠菜1");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setCreateTime(LocalDateTime.now());emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行新增员工的信息操作empMapper.insert(emp);System.out.println(emp.getId());}// 测试更新@Testpublic void testUpdate(){// 构造员工对象Emp emp = new Emp();emp.setId(19);emp.setUsername("Spring");emp.setName("春天的菠菜");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行更新员工的信息操作empMapper.update(emp);}// 根据员工ID查询员工@Testpublic void testGetById(){Emp emp = empMapper.getById(19);System.out.println(emp);}// 条件查询@Testpublic void testList(){List<Emp> listEmp = empMapper.list("张", (short) 1, LocalDate.of(2010, 1, 1), LocalDate.of(2020, 1, 1));System.out.println(listEmp);}}
3.7.3 使用concat解决使用'%$name}%'问题
修改EmpMapper接口
package com.runa.mapper;import com.runa.pojo.Emp;
import org.apache.ibatis.annotations.*;import java.time.LocalDate;
import java.util.List;@Mapper
public interface EmpMapper {// 根据id删除数据@Delete("delete from emp where id = #{id}")public void delete(Integer id);// 根据id删除数据,并获取返回值
// @Delete("delete from emp where id = #{id}")
// public int delete(Integer id);// 新增员工@Options(useGeneratedKeys = true, keyProperty = "id")@Insert("insert into emp" +"(username, name, gender, image, job, entrydate,dept_id, create_time, update_time)" +" VALUES(#{username},#{name},#{gender},#{image},#{job},#{entrydate},#{deptId},#{createTime},#{updateTime})")public void insert(Emp emp);// 更新员工信息@Update("update emp set username = #{username}, name = #{name}, gender = #{gender}, image = #{image}, " +"job = #{job}, entrydate = #{entrydate},dept_id = #{deptId}, update_time = #{updateTime} where id = #{id}")public void update(Emp emp);// 根据ID查询员工@Select("select * from emp where id = #{id}")public Emp getById(Integer id);// 根据ID查询员工, (不推荐)方案一:取别名方案
// @Select("select id,id, username, password, name, gender, image, job, entrydate, dept_id deptId, create_time createTime, update_time updateTime from emp where id = #{id}")
// public Emp getById(Integer id);// 根据ID查询员工 (不推荐)方案二:通过@Results, @Result注解手动映射封装
// @Results({
// @Result(column = "dept_id", property = "deptId"),
// @Result(column = "create_time", property = "createTime"),
// @Result(column = "update_time", property = "updateTime")
// })
// @Select("select * from emp where id = #{id}")
// public Emp getById(Integer id);// 条件查询员工 '%#{name}%' #{name} 不能出现在''里面所以改成$
// @Select("select * from emp where name like '%${name}%'and gender = #{gender} and entrydate between #{begin} and #{end} order by update_time desc ")
// public List<Emp> list(String name, Short gender, LocalDate begin, LocalDate end);// 条件查询员工 使用concat解决 '%${name}%'@Select("select * from emp where name like concat('%', #{name}, '%')and gender = #{gender} and entrydate between #{begin} and #{end} order by update_time desc ")public List<Emp> list(String name, Short gender, LocalDate begin, LocalDate end);}
以下图片可忽略

四 XML映射文件
4.1 XML映射规范

4.1.1 第一步:

EmpMapper.xml文件如下:
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper></mapper>
4.1.2 第二步:
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.runa.mapper.EmpMapper"></mapper>
4.1.3 第三步
resultType : 表示单条记录所封装的类型

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.runa.mapper.EmpMapper"><!--id EmpMapper 方法名 resultType : 表示单条记录所封装的类型 --><select id="list2" resultType="com.runa.pojo.Emp">select * from emp where name like concat('%', #{name}, '%')and gender = #{gender} and entrydate between #{begin} and #{end} order by update_time desc</select></mapper>
4.1.4 验证
package com.runa;import com.runa.mapper.EmpMapper;
import com.runa.mapper.UserMapper;
import com.runa.pojo.Emp;
import com.runa.pojo.User;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;import java.sql.*;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;@SpringBootTest
class SpringbootMybatisQuickstartApplicationTests {// @Autowired // 注入
// private UserMapper userMapper;@Autowired //注入private EmpMapper empMapper;// @Test
// public void testListUser() {
// List<User> userList = userMapper.list();
// userList.stream().forEach(user -> {
// System.out.println(user);
// });
// }@Testpublic void testDelete(){empMapper.delete(17);}// @Test // 获取返回值
// public void testDelete(){
// int id = empMapper.delete(16);
// System.out.println(id);
// }// 测试新增@Testpublic void testInsert(){// 构造员工对象Emp emp = new Emp();emp.setUsername("Bocai1");emp.setName("菠菜1");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setCreateTime(LocalDateTime.now());emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行新增员工的信息操作empMapper.insert(emp);System.out.println(emp.getId());}// 测试更新@Testpublic void testUpdate(){// 构造员工对象Emp emp = new Emp();emp.setId(19);emp.setUsername("Spring");emp.setName("春天的菠菜");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行更新员工的信息操作empMapper.update(emp);}// 根据员工ID查询员工@Testpublic void testGetById(){Emp emp = empMapper.getById(19);System.out.println(emp);}// 条件查询@Testpublic void testList(){List<Emp> listEmp = empMapper.list("张", (short) 1, LocalDate.of(2010, 1, 1), LocalDate.of(2020, 1, 1));System.out.println(listEmp);}// 条件查询 使用xml@Testpublic void testList2(){List<Emp> listEmp = empMapper.list2("张", (short) 1, LocalDate.of(2010, 1, 1), LocalDate.of(2020, 1, 1));System.out.println(listEmp);}}

4.2 mybatisx插件

快速定位

4.3 总结

五 Mybatis的动态SQL

5.1 <if>
5.1.1 优化EmpMapper.xml
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.runa.mapper.EmpMapper"><!--id EmpMapper 方法名 resultType : 表示单条记录所封装的类型 --><select id="list2" resultType="com.runa.pojo.Emp">select *from emp<where><if test= "name != null">name like concat('%', #{name}, '%')</if><if test= "gender != null">and gender = #{gender}</if><if test= "begin != null and end != null">and entrydate between #{begin} and #{end}</if>order by update_time desc</where></select></mapper>


注意:<where></where> 会针对多条件查询过滤一些特有的and
5.1.2 案例

5.1.2.1 优化EmpMapper 新增一个方法update2
package com.runa.mapper;import com.runa.pojo.Emp;
import org.apache.ibatis.annotations.*;import java.time.LocalDate;
import java.util.List;@Mapper
public interface EmpMapper {// 根据id删除数据@Delete("delete from emp where id = #{id}")public void delete(Integer id);// 根据id删除数据,并获取返回值
// @Delete("delete from emp where id = #{id}")
// public int delete(Integer id);// 新增员工@Options(useGeneratedKeys = true, keyProperty = "id")@Insert("insert into emp" +"(username, name, gender, image, job, entrydate,dept_id, create_time, update_time)" +" VALUES(#{username},#{name},#{gender},#{image},#{job},#{entrydate},#{deptId},#{createTime},#{updateTime})")public void insert(Emp emp);// 更新员工信息@Update("update emp set username = #{username}, name = #{name}, gender = #{gender}, image = #{image}, " +"job = #{job}, entrydate = #{entrydate},dept_id = #{deptId}, update_time = #{updateTime} where id = #{id}")public void update(Emp emp);// 根据ID查询员工@Select("select * from emp where id = #{id}")public Emp getById(Integer id);// 根据ID查询员工, (不推荐)方案一:取别名方案
// @Select("select id,id, username, password, name, gender, image, job, entrydate, dept_id deptId, create_time createTime, update_time updateTime from emp where id = #{id}")
// public Emp getById(Integer id);// 根据ID查询员工 (不推荐)方案二:通过@Results, @Result注解手动映射封装
// @Results({
// @Result(column = "dept_id", property = "deptId"),
// @Result(column = "create_time", property = "createTime"),
// @Result(column = "update_time", property = "updateTime")
// })
// @Select("select * from emp where id = #{id}")
// public Emp getById(Integer id);// 条件查询员工 '%#{name}%' #{name} 不能出现在''里面所以改成$
// @Select("select * from emp where name like '%${name}%'and gender = #{gender} and entrydate between #{begin} and #{end} order by update_time desc ")
// public List<Emp> list(String name, Short gender, LocalDate begin, LocalDate end);// 条件查询员工 使用concat解决 '%${name}%'@Select("select * from emp where name like concat('%', #{name}, '%')and gender = #{gender} and entrydate between #{begin} and #{end} order by update_time desc ")public List<Emp> list(String name, Short gender, LocalDate begin, LocalDate end);// 条件查询员工使用xml方式public List<Emp> list2(String name, Short gender, LocalDate begin, LocalDate end);// 更新员工信息使用xml方式 使用<if>,使用动态sql方式public void update2(Emp emp);}
5.1.2.2 EmpMpapper.xml新增一个update2的sql
这里也使用了<set></set>标签
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.runa.mapper.EmpMapper"><!--id EmpMapper 方法名 resultType : 表示单条记录所封装的类型 --><select id="list2" resultType="com.runa.pojo.Emp">select *from emp<where><if test="name != null">name like concat('%', #{name}, '%')</if><if test="gender != null">and gender = #{gender}</if><if test="begin != null and end != null">and entrydate between #{begin} and #{end}</if>order by update_time desc</where></select><!-- 动态更新员工--><update id="update2">update emp <set><if test="username != null">username = #{username},</if><if test="name != null">name= #{name},</if><if test="gender != null">gender = #{gender},</if><if test="image != null">image = #{image},</if><if test="job != null">job = #{job},</if><if test="entrydate != null">entrydate = #{entrydate},</if><if test="deptId != null">dept_id = #{deptId},</if><if test="updateTime != null">update_time = #{updateTime}</if></set>where id=#{id}</update></mapper>
5.1.2.3 新增测试方法testUpdate2测试
package com.runa;import com.runa.mapper.EmpMapper;
import com.runa.mapper.UserMapper;
import com.runa.pojo.Emp;
import com.runa.pojo.User;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;import java.sql.*;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;@SpringBootTest
class SpringbootMybatisQuickstartApplicationTests {// @Autowired // 注入
// private UserMapper userMapper;@Autowired //注入private EmpMapper empMapper;// @Test
// public void testListUser() {
// List<User> userList = userMapper.list();
// userList.stream().forEach(user -> {
// System.out.println(user);
// });
// }@Testpublic void testDelete(){empMapper.delete(17);}// @Test // 获取返回值
// public void testDelete(){
// int id = empMapper.delete(16);
// System.out.println(id);
// }// 测试新增@Testpublic void testInsert(){// 构造员工对象Emp emp = new Emp();emp.setUsername("Bocai1");emp.setName("菠菜1");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setCreateTime(LocalDateTime.now());emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行新增员工的信息操作empMapper.insert(emp);System.out.println(emp.getId());}// 测试更新@Testpublic void testUpdate(){// 构造员工对象Emp emp = new Emp();emp.setId(19);emp.setUsername("Spring");emp.setName("春天的菠菜");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行更新员工的信息操作empMapper.update(emp);}// 根据员工ID查询员工@Testpublic void testGetById(){Emp emp = empMapper.getById(19);System.out.println(emp);}// 条件查询@Testpublic void testList(){List<Emp> listEmp = empMapper.list("张", (short) 1, LocalDate.of(2010, 1, 1), LocalDate.of(2020, 1, 1));System.out.println(listEmp);}// 条件查询 使用xml@Testpublic void testList2(){
// List<Emp> listEmp = empMapper.list2("张", (short) 1, LocalDate.of(2010, 1, 1), LocalDate.of(2020, 1, 1));List<Emp> listEmp = empMapper.list2("张", (short) 1, null, null);System.out.println(listEmp);}// 测试更新,使用动态sql 更新id为18的员工username bocai2 更新为 name菠菜大哥 更新为 gender更新为 2@Testpublic void testUpdate2(){// 构造员工对象Emp emp = new Emp();emp.setId(18);emp.setUsername("bocai2");emp.setName("菠菜大哥");emp.setDeptId(2);emp.setUpdateTime(LocalDateTime.now());// 执行更新员工的信息操作empMapper.update2(emp);}}
5.1.3 总结

5.2 <foreach>
5.2.1 优化EmpMapper 新增一个方法deleteByIds
package com.runa.mapper;import com.runa.pojo.Emp;
import org.apache.ibatis.annotations.*;import java.time.LocalDate;
import java.util.List;@Mapper
public interface EmpMapper {// 根据id删除数据@Delete("delete from emp where id = #{id}")public void delete(Integer id);// 根据id删除数据,并获取返回值
// @Delete("delete from emp where id = #{id}")
// public int delete(Integer id);// 新增员工@Options(useGeneratedKeys = true, keyProperty = "id")@Insert("insert into emp" +"(username, name, gender, image, job, entrydate,dept_id, create_time, update_time)" +" VALUES(#{username},#{name},#{gender},#{image},#{job},#{entrydate},#{deptId},#{createTime},#{updateTime})")public void insert(Emp emp);// 更新员工信息@Update("update emp set username = #{username}, name = #{name}, gender = #{gender}, image = #{image}, " +"job = #{job}, entrydate = #{entrydate},dept_id = #{deptId}, update_time = #{updateTime} where id = #{id}")public void update(Emp emp);// 根据ID查询员工@Select("select * from emp where id = #{id}")public Emp getById(Integer id);// 批量删除员工public void deleteByIds(List<Integer> ids);// 根据ID查询员工, (不推荐)方案一:取别名方案
// @Select("select id,id, username, password, name, gender, image, job, entrydate, dept_id deptId, create_time createTime, update_time updateTime from emp where id = #{id}")
// public Emp getById(Integer id);// 根据ID查询员工 (不推荐)方案二:通过@Results, @Result注解手动映射封装
// @Results({
// @Result(column = "dept_id", property = "deptId"),
// @Result(column = "create_time", property = "createTime"),
// @Result(column = "update_time", property = "updateTime")
// })
// @Select("select * from emp where id = #{id}")
// public Emp getById(Integer id);// 条件查询员工 '%#{name}%' #{name} 不能出现在''里面所以改成$
// @Select("select * from emp where name like '%${name}%'and gender = #{gender} and entrydate between #{begin} and #{end} order by update_time desc ")
// public List<Emp> list(String name, Short gender, LocalDate begin, LocalDate end);// 条件查询员工 使用concat解决 '%${name}%'@Select("select * from emp where name like concat('%', #{name}, '%')and gender = #{gender} and entrydate between #{begin} and #{end} order by update_time desc ")public List<Emp> list(String name, Short gender, LocalDate begin, LocalDate end);// 条件查询员工使用xml方式public List<Emp> list2(String name, Short gender, LocalDate begin, LocalDate end);// 更新员工信息使用xml方式 使用<if>,使用动态sql方式public void update2(Emp emp);}
5.2.2 EmpMpapper.xml新增一个deleteByIds的sql
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.runa.mapper.EmpMapper"><!--id EmpMapper 方法名 resultType : 表示单条记录所封装的类型 --><select id="list2" resultType="com.runa.pojo.Emp">select *from emp<where><if test="name != null">name like concat('%', #{name}, '%')</if><if test="gender != null">and gender = #{gender}</if><if test="begin != null and end != null">and entrydate between #{begin} and #{end}</if>order by update_time desc</where></select><!-- 动态更新员工--><update id="update2">update emp<set><if test="username != null">username = #{username},</if><if test="name != null">name= #{name},</if><if test="gender != null">gender = #{gender},</if><if test="image != null">image = #{image},</if><if test="job != null">job = #{job},</if><if test="entrydate != null">entrydate = #{entrydate},</if><if test="deptId != null">dept_id = #{deptId},</if><if test="updateTime != null">update_time = #{updateTime}</if></set>where id=#{id}</update><!-- 批量删除员工 (18,19,20)--><!--collection : 要遍历的集合item : 遍历出来的元素separator : 分隔符open :遍历开始前拼接的sql片段close : 遍历结束后拼接的sql片段)--><delete id="deleteByIds">delete from emp where id in<foreach collection="ids" item="id" separator="," open="(" close=")">#{id}</foreach></delete>
</mapper>
5.2.3 新增测试方法testDeleteByids
package com.runa;import com.runa.mapper.EmpMapper;
import com.runa.mapper.UserMapper;
import com.runa.pojo.Emp;
import com.runa.pojo.User;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;import java.sql.*;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;@SpringBootTest
class SpringbootMybatisQuickstartApplicationTests {// @Autowired // 注入
// private UserMapper userMapper;@Autowired //注入private EmpMapper empMapper;// @Test
// public void testListUser() {
// List<User> userList = userMapper.list();
// userList.stream().forEach(user -> {
// System.out.println(user);
// });
// }@Testpublic void testDelete(){empMapper.delete(17);}// @Test // 获取返回值
// public void testDelete(){
// int id = empMapper.delete(16);
// System.out.println(id);
// }// 测试新增@Testpublic void testInsert(){// 构造员工对象Emp emp = new Emp();emp.setUsername("Bocai1");emp.setName("菠菜1");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setCreateTime(LocalDateTime.now());emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行新增员工的信息操作empMapper.insert(emp);System.out.println(emp.getId());}// 测试更新@Testpublic void testUpdate(){// 构造员工对象Emp emp = new Emp();emp.setId(19);emp.setUsername("Spring");emp.setName("春天的菠菜");emp.setImage("1.jpg");emp.setGender((short)1);emp.setJob((short)1);emp.setEntrydate(LocalDate.of(2023, 2,27));emp.setUpdateTime(LocalDateTime.now());emp.setDeptId(1);// 执行更新员工的信息操作empMapper.update(emp);}// 根据员工ID查询员工@Testpublic void testGetById(){Emp emp = empMapper.getById(19);System.out.println(emp);}// 条件查询@Testpublic void testList(){List<Emp> listEmp = empMapper.list("张", (short) 1, LocalDate.of(2010, 1, 1), LocalDate.of(2020, 1, 1));System.out.println(listEmp);}// 条件查询 使用xml@Testpublic void testList2(){
// List<Emp> listEmp = empMapper.list2("张", (short) 1, LocalDate.of(2010, 1, 1), LocalDate.of(2020, 1, 1));List<Emp> listEmp = empMapper.list2("张", (short) 1, null, null);System.out.println(listEmp);}// 测试更新,使用动态sql 更新id为18的员工username bocai2 更新为 name菠菜大哥 更新为 gender更新为 2@Testpublic void testUpdate2(){// 构造员工对象Emp emp = new Emp();emp.setId(18);emp.setUsername("bocai2");emp.setName("菠菜大哥");emp.setDeptId(2);emp.setUpdateTime(LocalDateTime.now());// 执行更新员工的信息操作empMapper.update2(emp);}// 批量删除员工 13 、 14、 15@Testpublic void testDeleteByids(){List<Integer> ids = Arrays.asList(13, 14, 15);empMapper.deleteByIds(ids);}}

5.2.4 总结

5.3 <sql><include>
存在大量重复的sql

解决方案
5.3.1 EmpMpapper.xml新增sql 标签优化list2 include标签
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Mapper 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.runa.mapper.EmpMapper"><sql id="commonSelect">select id,id, username, password, name, gender, image, job, entrydate, dept_id deptId, create_time createTime, update_time updateTime from emp</sql><!--id EmpMapper 方法名 resultType : 表示单条记录所封装的类型 --><select id="list2" resultType="com.runa.pojo.Emp"><include refid="commonSelect"></include><where><if test="name != null">name like concat('%', #{name}, '%')</if><if test="gender != null">and gender = #{gender}</if><if test="begin != null and end != null">and entrydate between #{begin} and #{end}</if>order by update_time desc</where></select><!-- 动态更新员工--><update id="update2">update emp<set><if test="username != null">username = #{username},</if><if test="name != null">name= #{name},</if><if test="gender != null">gender = #{gender},</if><if test="image != null">image = #{image},</if><if test="job != null">job = #{job},</if><if test="entrydate != null">entrydate = #{entrydate},</if><if test="deptId != null">dept_id = #{deptId},</if><if test="updateTime != null">update_time = #{updateTime}</if></set>where id=#{id}</update><!-- 批量删除员工 (18,19,20)--><!--collection : 要遍历的集合item : 遍历出来的元素separator : 分隔符open :遍历开始前拼接的sql片段close : 遍历结束后拼接的sql片段)--><delete id="deleteByIds">delete from emp where id in<foreach collection="ids" item="id" separator="," open="(" close=")">#{id}</foreach></delete>
</mapper>
5.3.2 执行测试方法testList2


5.4 总结

相关文章:
[JavaWeb]【八】web后端开发-Mybatis
目录 一 介绍 二 Mybatis的入门 2.1 快速入门 2.1.1 准备SpringBoot工程 2.1.2 创建数据库mybatis以及对应库表user 2.1.3 创建User实体类 2.1.4 配置application.properties数据库连接信息 2.1.5 编写sql语句(注解方式) 2.1.6 测试运行 2.1.7 配…...
Flink源码之Checkpoint执行流程
Checkpoint完整流程如上图所示: JobMaster的CheckpointCoordinator向所有SourceTask发送RPC触发一次CheckPointSourceTask向下游广播CheckpointBarrierSouceTask完成状态快照后向JobMaster发送快照结果非SouceTask在Barrier对齐后完成状态快照向JobMaster发送快照结…...
【工具使用】Git的使用
dev代表开发版 1. git clone 命令 通过 git add <name> 对文件进行跟踪,把<name>加入到暂存区 git commit -m XXXXXXX 提交修改并补充XXXXX作为注释 “暂存”状态:出现了一些修改,但是还没有提交 对于Java来说,.cl…...
无涯教程-PHP Installation on Windows NT/2000/XP with IIS函数
在Windows Server上运行IIS的PHP的安装比在Unix上简单得多,因为它涉及的是预编译的二进制文件而不是源代码。 如果您打算在Windows上安装PHP,那么这是先决条件列表- 运行中的PHP支持的Web服务器。一个正确安装的PHP支持的数据库,如MySQL或Oracle等。(如果您打算使用的话) PHP…...
EureKa快速入门
EureKa快速入门 远程调用的问题 多个服务有多个端口,这样的话服务有多个,硬编码不太适合 eureKa的作用 将service的所有服务的端口全部记录下来 想要的话 直接从注册中心查询对于所有服务 每隔一段时间需要想eureKa发送请求 保证服务还存活 动手实践 …...
Sectigo EV代码签名申请步骤
一、EV代码签名申请前提 1、单位成立时间不低于:3个月 2、单位工商及企查查可查 3、单位经营正常 4、注册地址真实存在,禁止使用集中注册地址 5、企查查登记电话和邮箱,确定查询结果的电话可以接听、邮箱可以接收邮件,如果信…...
生信学院|08月25日《SOLIDWORKS PDM帮助企业对设计数据版本的管理应用》
课程主题:SOLIDWORKS PDM帮助企业对设计数据版本的管理应用 课程时间:2023年08月25日 14:00-14:30 主讲人:车立洋 生信科技 PDM专家 1、图纸&文档的版本管理对于企业的重要性 2、SolidWorks PDM对图纸&文档版本的管理 3、SolidW…...
vue页面转pdf后分页时文字被横向割裂
效果 预期效果 //避免分页被截断async outPutPdfFn (id, title) {const _t this;const A4_WIDTH 592.28;const A4_HEIGHT 841.89;// dom的id。let target document.getElementById(pdf);let pageHeight target.scrollWidth / A4_WIDTH * A4_HEIGHT;// 获取分割dom…...
数据结构——队列(C语言)
需求:无 本篇文章将解决一下几个问题: 队列是什么?如何实现一个队列?什么场景下会用队列? 队列的概念: 队列:一种只允许一端进行插入数据操作,在另一端进行删除操作的特殊线性表。…...
WGS84地球坐标系,GCJ02火星坐标系,BD09百度坐标系简介与转换 资料收集
野火 ATGM332D简介 高性能、低功耗 GPS、北斗双模定位模块 STM32 GPS定位_为了维护世界和平_的博客-CSDN博客 秉火多功能调试助手上位机开源!共六款软件,学到你吐... , - 电脑上位机 - 野火电子论坛 - Powered by Discuz! https://www.firebbs.cn/for…...
【面试题】前端面试复习6---性能优化
前端面试题库 (面试必备) 推荐:★★★★★ 地址:前端面试题库 性能优化 一、性能指标 要在 Chrome 中查看性能指标,可以按照以下步骤操作: 打开 Chrome 浏览器,并访问你想要测试…...
隧道HTTP具备的条件
作为一名专业的爬虫代理供应商,我们都知道使用代理是保证爬虫的高效性和稳定性的重要手段之一。而隧道代理则是近年来备受推崇的一种代理形式,它通过将请求通过隧道传输,可以有效地隐藏爬虫的真实IP地址,提高爬虫的反爬能力。 在…...
部署FTP服务(二)
目录 2.访问FTP服务 1.使用ftp命令行工具 2.使用浏览器 3.使用FileZilla Client 3.Serv-U 1.定义新域 2.创建用户 4. windowsserver搭建ftp服务器 一、FTP工具 二、Windows资源管理器 三、IE浏览器访问 2.访问FTP服务 下面在一台装有Windows10操作系统的计算机中&#…...
缓存的变更(JVM本地缓存->Redis分布式缓存)
在一次需求修改中,下游的服务附加提出了,针对某个业务数据缓存的生效时间的要求 原JVM设计方案: 采用jvm本地缓存机制,定时任务30秒刷新一次 现在redis方案: 因为很多地方使用了这个业务数据缓存,使用方…...
springMVC Unix 文件参数变更漏洞修复
错误信息如下: 解决方案: 原因:未对用户输入正确执行危险字符清理 未检查用户输入中是否包含“…”(两个点)字符串,比如 url 为 /login?action…/webapps/RTJEKSWTN26635&typerandomCode cookie为Coo…...
【LeetCode】494.目标和
题目 给你一个非负整数数组 nums 和一个整数 target 。 向数组中的每个整数前添加 或 - ,然后串联起所有整数,可以构造一个 表达式 : 例如,nums [2, 1] ,可以在 2 之前添加 ,在 1 之前添加 - &#x…...
KaiwuDB 荣获哈佛商业评论 2023“高能韧性团队奖”
8月18日,《哈佛商业评论》中文版携手 FESCO 成功举办“第九届人才经济论坛”暨“2022-2023 高能团队奖颁奖典礼”。论坛秉承前沿的全球视野及权威的管理理念,发掘并展示本土企业组织管理的最佳实践,并重磅揭晓第二届“高能团队奖”评选结果。…...
删除ubuntu开始菜单中的图标
背景 本来是很好看干净的界面 更新谷歌浏览器后出现了Gmail,幻灯片,谷歌硬盘等跟谷歌相关的乱七八糟东西搞得界面就很丑 解决问题 删掉那个图标 输入命令 sudo nautilus /usr/share/applicationssudo nautilus ~/.local/share/applications可以…...
信息系统项目管理基础知识学习笔记 - IT 治理基础 - IT治理的驱动因素
信息系统项目管理基础知识学习笔记 - IT 治理基础 - IT治理的驱动因素 IT治理的驱动因素组织的IT战略驱动组织开展高质量IT治理因素IT治理的内涵IT 治理体系信息系统项目管理基础知识学习笔记 - IT 治理基础 - IT治理的驱动因素 IT治理的驱动因素 组织信息系统建设和运行需要…...
8月21-22日上课内容 第一章 MySQL数据库初始
本章结构 数据库的基本概念 概述(总览) 结构: 数据 表 数据库 数据库管理系统 数据库系统原理 数据 (Data) 描述事物的符号记录 包括数字,文字、图形、图像、声音、档案记录等以“记录”形式按统一的格式进行存储表 将不同…...
ROS2开发避坑:用CycloneDDS配置文件解决本地回环通信中断问题(附完整XML)
ROS2通信稳定性实战:CycloneDDS深度配置指南 当你在机器人开发过程中遭遇节点间通信时断时续的问题,那种感觉就像在暴雨天试图用对讲机协调团队——关键指令总在最重要时刻丢失。本文将揭示如何通过CycloneDDS的精细配置,在硬件网络不稳定的…...
M2LOrder模型在AI编程助手场景的应用:代码注释情感分析
M2LOrder模型在AI编程助手场景的应用:代码注释情感分析 1. 引言 你有没有在代码注释里写过“这里有个天坑,后面的人小心”或者“TODO: 这个逻辑太绕了,得重构”?这些看似随手的吐槽,其实藏着开发者最真实的情绪。代码…...
Python: 多优化算法TSP求解方案,物流路径规划代码实践 - 附详尽注释及标准数据集
Python:模拟退火算法、蚁群算法、遗传算法、粒子群算法求解旅行商问题(TSP)的Python代码程序。 物流路径规划问题。 -- 数据集采用的tsplib标准数据集,可以根据自己需求修改城市坐标。 代码完整,注释详细,打印每次迭代结果&#x…...
HelixDB部署与运维:从本地开发到生产环境的完整流程
HelixDB部署与运维:从本地开发到生产环境的完整流程 【免费下载链接】helix-db HelixDB is a powerful, graph-vector database built entirely in Rust for millisecond query latency and ease of use. 项目地址: https://gitcode.com/gh_mirrors/he/helix-db …...
终极免费抖音无水印视频下载完整教程:3步快速获取高清素材
终极免费抖音无水印视频下载完整教程:3步快速获取高清素材 【免费下载链接】douyin-downloader A practical Douyin downloader for both single-item and profile batch downloads, with progress display, retries, SQLite deduplication, and browser fallback s…...
Windows更新修复新范式:Reset-Windows-Update-Tool的系统化解决方案
Windows更新修复新范式:Reset-Windows-Update-Tool的系统化解决方案 【免费下载链接】Reset-Windows-Update-Tool Troubleshooting Tool with Windows Updates (Developed in Dev-C). 项目地址: https://gitcode.com/gh_mirrors/re/Reset-Windows-Update-Tool …...
Windows右键菜单重构指南:从混乱到高效的ContextMenuManager实战
Windows右键菜单重构指南:从混乱到高效的ContextMenuManager实战 【免费下载链接】ContextMenuManager 🖱️ 纯粹的Windows右键菜单管理程序 项目地址: https://gitcode.com/gh_mirrors/co/ContextMenuManager 问题诊断:你的右键菜单是…...
实战-EdgeBoard赛事卡:从零部署飞桨模型到智能车竞赛
1. EdgeBoard赛事卡开箱与环境准备 第一次拿到EdgeBoard赛事专用卡时,这块巴掌大的小盒子让我有点怀疑——这么小的板子真能跑动智能车竞赛需要的视觉模型吗?拆开包装后发现,除了板卡本体,配件只有一根Type-C线,确实符…...
Zotero重复条目智能处理指南:从混乱到有序的文献管理解决方案
Zotero重复条目智能处理指南:从混乱到有序的文献管理解决方案 【免费下载链接】ZoteroDuplicatesMerger A zotero plugin to automatically merge duplicate items 项目地址: https://gitcode.com/gh_mirrors/zo/ZoteroDuplicatesMerger 学术研究中ÿ…...
Magisk完整实践指南:从Root权限获取到系统级定制
Magisk完整实践指南:从Root权限获取到系统级定制 【免费下载链接】Magisk The Magic Mask for Android 项目地址: https://gitcode.com/GitHub_Trending/ma/Magisk Magisk作为Android系统Root权限管理的主流解决方案,提供了系统级定制能力而无需修…...

修改后: