Mybatis学习笔记-复杂查询

- 多个学生,对应一个老师
- 对于学生而言,关联:多个学生关联一个老师【多对一】
- 对于老师而言,集合:一个老师,有多个学生【一对多】
复杂查询环境搭建
数据库搭建
CREATE TABLE `teacher` (
`id` INT(10) NOT NULL,
`name` VARCHAR(30) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=INNODB DEFAULT CHARSET=utf8
INSERT INTO teacher(`id`, `name`) VALUES (1, 秦老师);
CREATE TABLE `student` (
`id` INT(10) NOT NULL,
`name` VARCHAR(30) DEFAULT NULL,
`tid` INT(10) DEFAULT NULL,
PRIMARY KEY (`id`),
KEY `fktid` (`tid`),
CONSTRAINT `fktid` FOREIGN KEY (`tid`) REFERENCES `teacher` (`id`)
) ENGINE=INNODB DEFAULT CHARSET=utf8INSERT INTO `student` (`id`, `name`, `tid`) VALUES (1, 小明, 1);
INSERT INTO `student` (`id`, `name`, `tid`) VALUES (2, 小红, 1);
INSERT INTO `student` (`id`, `name`, `tid`) VALUES (3, 小张, 1);
INSERT INTO `student` (`id`, `name`, `tid`) VALUES (4, 小李, 1);
INSERT INTO `student` (`id`, `name`, `tid`) VALUES (5, 小王, 1);

创建Maven项目
- pom.xml配置所使用的依赖
<!--导入依赖-->
<dependencies>
<!-- https://mvnrepository.com/artifact/org.mybatis/mybatis -->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.5.7</version>
</dependency>
<!--数据库连接-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.22</version>
</dependency>
<!--Junit测试单元-->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.13</version>
<scope>test</scope>
</dependency>
</dependencies>
- Mybatis核心配置文件
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN" "http://mybatis.org/dtd/mybatis-3-config.dtd" >
<!--核心配置文件-->
<configuration>
<!--引入外部配置文件(db.properties)-->
<properties resource="db.properties"/>
<settings>
<!--标准日志工厂实现-->
<setting name="logImpl" value="STDOUT_LOGGING"/>
</settings>
<!--引入别名(扫描包)-->
<typeAliases>
<package name="cn.iris.pojo"/>
</typeAliases>
<!--配置环境-->
<environments default="test">
<environment id="test">
<transactionManager type="JDBC"/>
<dataSource type="POOLED">
<property name="driver" value="${driver}"/>
<property name="url" value="${url}"/>
<property name="username" value="${username}"/>
<property name="password" value="${password}"/>
</dataSource>
</environment>
</environments>
</configuration>
- 创建项目包结构(pojo,dao,utils)
- pojo
- Student
- Teacher
- Dao
- StudentMapper
- TeacherMapper
- Utils
- MybatisUtil
package cn.iris.utils;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import java.io.IOException;
import java.io.InputStream;
// SqlSessionFactory --> SqlSession
public class MybatisUtils {
private static SqlSessionFactory sqlSessionFactory;
static {
try {
// 使用Mybatis获取SqlSessionFactory对象
String resource = "mybatis-config.xml";
InputStream inputStream = Resources.getResourceAsStream(resource);
sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
} catch (IOException e) {
e.printStackTrace();
}
}
// 有了 SqlSessionFactory,我们可以从中获得 SqlSession 的实例
public static SqlSession getSqlSession() {
return sqlSessionFactory.openSession();
}
}
- 编写实体类
- Class Teacher
package cn.iris.pojo;
public class Teacher {
private int id;
private String name;
public Teacher() {}
public Teacher(int id, String name) {
this.id = id;
this.name = name;
}
Setter&Getter
@Override
public String toString()
}
- Class Student
package cn.iris.pojo;
public class Student {
private int id;
private String name;
private Teacher teacher;
public Student(int id, String name, Teacher teacher) {
this.id = id;
this.name = name;
this.teacher = teacher;
}
public Student() {
}
Setter&Getter
@Override
public String toString()
}
- 编写与实体类绑定的Mapper.xml
- resource.cn.iris.dao
- 一定要在核心配置文件中注册Mapper.xml
<!--以TeacherMapper为例-->
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="cn.iris.dao.TeacherMapper">
</mapper>
测试环境搭建
- TeacherMapper中测试getTeacherById()方法
// 使用注解进行简单查询测试
@Select("SELECT * FROM teacher WHERE id = #{id}")
Teacher getTeacherById(@Param("id") int id);
多对一 具体代码实现
查询所有学生以及其对应的老师信息
<!--思路:
1. 查询所有的学生信息
2. 根据学生tid 寻找 对应的老师
-->
方法一
- 查询嵌套【子查询处理】
<select id="getStudent" resultMap="StudentTeacher">
SELECT * FROM student;
</select>
<resultMap id="StudentTeacher" type="Student">
<result property="id" column="id"/>
<result property="name" column="name"/>
<!--复杂属性需要单独处理
对象:association 集合:collection-->
<!--property 属性名
column 字段名
javaType 对应的Java对象(全类名/别名)
select 嵌套查询
-->
<association property="teacher" column="tid" javaType="Teacher" select="getTeacher"/>
</resultMap>
<select id="getTeacher" resultType="Teacher">
SELECT * FROM teacher WHERE id = #{tid};
</select>
方法二
- 按照结果嵌套处理【SQL联表查询】
<select id="getStudent2" resultMap="StudentTeacher2">
SELECT s.id sid,s.name sname,t.id tid,t.name tname FROM student s, teacher t
WHERE s.tid = t.id;
</select>
<resultMap id="StudentTeacher2" type="Student">
<result property="id" column="sid"/>
<result property="name" column="sname"/>
<association property="teacher" javaType="Teacher">
<result property="name" column="tname"/>
<result property="id" column="tid"/>
</association>
</resultMap>
一对多 具体代码实现
环境搭建
- Class Teacher
package cn.iris.pojo;
public class Student {
private int id;
private String name;
private int tid;
public Student() {
}
public Student(int id, String name, int tid) {
this.id = id;
this.name = name;
this.tid = tid;
}
Setter&Getter
@Override
public String toString()
}
}
- Class Student
package cn.iris.pojo;
import java.util.List;
public class Teacher {
private int id;
private String name;
private List<Student> students;
public Teacher(){}
public Teacher(int id, String name, List<Student> students) {
this.id = id;
this.name = name;
this.students = students;
}
Setter&Getter
@Override
public String toString()
}
}
查询指定ID老师及其全部学生
- 【联表查询】结果集嵌套处理
<!--按结果嵌套查询-->
<select id="getTeacherStudents" resultMap="TeacherStudent">
SELECT s.id sid, s.name sname, t.id tid,t.name tname FROM student s, teacher t
WHERE s.tid = t.id AND t.id = #{id};
</select>
<resultMap id="TeacherStudent" type="Teacher">
<result property="id" column="tid"/>
<result property="name" column="tname"/>
<collection property="students" ofType="Student">
<result property="id" column="sid"/>
<result property="name" column="sname"/>
<result property="tid" column="tid"/>
</collection>
</resultMap>
- 【子查询】查询嵌套
<!--子查询-->
<select id="getTeacherStudents2" resultMap="TeacherStudent2">
SELECT * FROM teacher WHERE id = #{id}
</select>
<resultMap id="TeacherStudent2" type="Teacher">
<result property="id" column="id"/>
<result property="name" column="name"/>
<collection property="students" javaType="ArrayList" ofType="Student" select="getStudent" column="id"/>
</resultMap>
<select id="getStudent" resultType="Student">
SELECT * FROM student WHERE tid = #{tid}
</select>
总结
- 关联 - association【多对一】
- 集合 - collection【一对多】
- javaType & ofType
- javaType:用来指定实体类中属性类型
- ofType:用来指定指定映射到List/集合中的pojo类型(泛型中的约束类型)
- 注意点
- 确保SQL的可读性(通俗易懂)
- 注意【一对多】和【多对一】中的属性名&字段问题
- 如果问题不好排错 --> 使用日志,查看log文件
- Mybatis执行流程

【面试涉及问题】
- Mysql引擎
https://www.jianshu.com/p/4bb9f78b4f6d - InnoDB底层原理
https://www.jianshu.com/p/9b83ea78b380 - 索引&索引优化
https://www.cnblogs.com/kexinxin/p/11537898.html
Mybatis学习笔记-复杂查询的更多相关文章
- mybatis学习笔记(14)-查询缓存之中的一个级缓存
mybatis学习笔记(14)-查询缓存之中的一个级缓存 标签: mybatis mybatis学习笔记14-查询缓存之中的一个级缓存 查询缓存 一级缓存 一级缓存工作原理 一级缓存測试 一级缓存应用 ...
- Mybatis学习笔记导航
Mybatis小白快速入门 简介 本人是一个Java学习者,最近才开始在博客园上分享自己的学习经验,同时帮助那些想要学习的uu们,相关学习视频在小破站的狂神说,狂神真的是我学习到现在觉得最GAN的老师 ...
- MyBatis:学习笔记(3)——关联查询
MyBatis:学习笔记(3)--关联查询 关联查询 理解联结 SQL最强大的功能之一在于我们可以在数据查询的执行中可以使用联结,来将多个表中的数据作为整体进行筛选. 模拟一个简单的在线商品购物系统, ...
- mybatis学习笔记(10)-一对一查询
mybatis学习笔记(10)-一对一查询 标签: mybatis mybatis学习笔记10-一对一查询 resultType实现 resultMap实现 resultType和resultMap实 ...
- Mybatis学习笔记(二) 之实现数据库的增删改查
开发环境搭建 mybatis 的开发环境搭建,选择: eclipse j2ee 版本,mysql 5.1 ,jdk 1.7,mybatis3.2.0.jar包.这些软件工具均可以到各自的官方网站上下载 ...
- MyBatis:学习笔记(1)——基础知识
MyBatis:学习笔记(1)--基础知识 引入MyBatis JDBC编程的问题及解决设想 ☐ 数据库连接使用时创建,不使用时就释放,频繁开启和关闭,造成数据库资源浪费,影响数据库性能. ☐ 使用数 ...
- Mybatis学习笔记二
本篇内容,紧接上一篇内容Mybatis学习笔记一 输入映射和输出映射 传递简单类型和pojo类型上篇已介绍过,下面介绍一下包装类型. 传递pojo包装对象 开发中通过可以使用pojo传递查询条件.查询 ...
- Mybatis学习笔记之二(动态mapper开发和spring-mybatis整合)
一.输入映射和输出映射 1.1 parameterType(输入类型) [传递简单类型] 详情参考Mybatis学习笔记之一(环境搭建和入门案例介绍) 使用#{}占位符,或者${}进行sql拼接. [ ...
- mybatis学习笔记--常见的错误
原文来自:<mybatis学习笔记--常见的错误> 昨天刚学了下mybatis,用的是3.2.2的版本,在使用过程中遇到了些小问题,现总结如下,会不断更新. 1.没有在configurat ...
随机推荐
- Kubernetes的认证机制
1.了解认证机制 API服务器可以配置一到多个认证的插件(授权插件同样也可以).API服务器接收到的请求会经过一个认证插件的列表,列表中的每个插件都可以检查这个请求和尝试确定谁在发送这个请求.列表中的 ...
- 从零开始学前端,React框架背后的核心机制和原理JSX
什么是React React是起源于Facebook的一个前端框架,用于构建用户界面的JavaScript库,Facebook用来探索一种更加高效优雅的Javascript MVC框架来架设Insta ...
- 测试开发:推荐一款阿里最新 Python 自动化开源工具!
大家好,我是麦小米,是狂师老师全栈测开训练营中的一名学员. 如果之前做过iOS自动化的同学相信都知道,一直以来,iOS自动化的实现&执行都必须依赖 Mac 系统,其主要原因是因为需要通过 xc ...
- Linux中重要目录详解
Linux重要目录详解 / 根目录,第一层目录,所有其他目录的根,一般根目录下只存放目录.包括:/bin, /boot, /dev, /etc, /home, /lib, /mnt, /opt, /p ...
- 20、oralce中单引号和双引号的区别
20.oralce中单引号和双引号的区别: 20.1.单引号和双引号oracle都支持,但是两者是有区别的: 20.2.双引号在 Oracle 中的作用: 1.双引号的作用是:假如建立对象的时候,对象 ...
- webpack(4)webpack.config.js配置和package.json配置
前言 上一篇文章我们使用webpack打包成功了,但是每次都要自己手动输入打包的文件地址和打包到哪里去的地址,非常麻烦,所以这里介绍使用配置文件进行打包 webpack.config.js 首先我们创 ...
- CentOS-yum安装Docker环境(含:常用命令)
安装Docker环境 $ yum install docker -y 启动Docker $ systemctl start docker 设置自启动 $ systemctl enable docker ...
- CG-CTF single
一.拖入ida,先静态分析一下 发现有三个函数,点击进去看看 a1为0时,当a2[i]为0时,将自身的值赋值到该位置,a1为0时,就不需要动. 这三个函数都是在暗示这东西是个数独,每行每列,都有1到9 ...
- Sharding+SpringBoot+Mybatis 读写分离
基于Sharding JDBC的读写分离 1.引入pom.xml <dependencies> <!-- mybatis --> <dependency> < ...
- 软件测试跟踪工具Bugzilla的安装 - Linux版本
首先查看Linux当前版本 输入"uname -a ",可显示电脑以及操作系统的相关信息 输入"cat /proc/version",说明正在运行的内核版本 输 ...