涉及到resultMap 标签 复杂的resultMap 处理字段名不一致
- 多个学生,对应一个老师
- 对于学生这边而言, 关联 .. 多个学生,关联一个老师 【多对一】
- 对于老师而言, 集合 , 一个老师,有很多学生 【一对多】
一 多对一关系 关联 association
前提:数据库创建相应的表
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=utf8
INSERT 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');
测试环境的搭建:
- 导入lombok
- 新建实体类 Teacher,Student
- 建立Mapper接口
- 建立Mapper.XML文件
- 在核心配置文件中绑定注册我们的Mapper接口或者文件!【方式很多,随心选】
- 测试查询是否能够成功!
Student类:
@Data
public class Student {
private int id;
private String name;
//学生需要关联一个老师 数据库当中外键
private Teacher teacher;
Teacher类:
@Data
public class Teacher {
private int id;
private String name;
}
在StudentMapper.xml文件当中:
方式一:按照查询条件嵌套去查询
需求:获取所有学生及对应老师的信息
思路:
1. 获取所有学生的信息
2. 根据获取的学生信息的老师ID->获取该老师的信息
3. 思考问题,这样学生的结果集中应该包含老师,该如何处理呢,数据库中我们一般使用关联查询?
1. 做一个结果集映射:StudentTeacherZichaxunMap
2. StudentTeacherZichaxunMap结果集的类型为 Student
3. 学生中老师的属性为teacher,对应数据库中为tid。
多个 [1,...)学生关联一个老师=> 一对一,一对多
4. 查看官网找到:association – 一个复杂类型的关联;使用它来处理关联查询
<!--子查询 相当于 select * from student where id={select。。。。} --> <select id="getStudentTeacher2" resultMap="StudentTeacherZichaxunMap"> select * from student </select> <resultMap id="StudentTeacherZichaxunMap" type="Student"> <result property="id" column="id"/> <result property="name" column="name"/> <!--association关联属性 property属性名 javaType属性类型 column在多的一方的表中的列名--> <association property="teacher" column="tid" javaType="Teacher" select="getTeacher"/> <!-- 这里传递过来的id,只有一个属性的时候,下面可以写任何值 association中column多参数配置: column="{key=value,key=value}" 其实就是键值对的形式,key是传给下个sql的取值名称,value是片段一中sql查询的字段名。 --> </resultMap> <select id="getTeacher" resultMap="teacherMap" > select * from teacher </select> <resultMap id="teacherMap" type="Teacher"> <result property="id" column="id"></result> <result property="name" column="name"></result> </resultMap>
方式二: 按照结果嵌套查询 主要解决字段名不一致的问题
<!--连表查询 从结果嵌套处理- 从需要显示的字段当中映射字段名不一致的现象--> <select id="getStudentTeacher1" resultMap="StudentTeacherMap"> select s.id sid,s.name sname, t.name tname from student s,teacher t where t.id=s.tid; </select> <resultMap id="StudentTeacherMap" type="Student"> <result property="id" column="id"/> <result property="name" column="name"/> <!--关联对象property 关联对象在Student实体类中的属性--> <association property="teacher" javaType="Teacher"> <result property="name" column="tname"/> </association> </resultMap>
总结:
多对一关系 关联 association
<!--association关联属性 property属性名 javaType属性类型 column在多的一方的表中的列名-->
方式有两种:
- 按照结果嵌套查询。就是正常的连表查询 关键需要解决字段不一致的问题
- 按照查询条件查询。就是子查询 select当中还有select。select * from student where id={select。。。。}
二 一对多关系 集合 collection
一个老师拥有多个学生
对老师而言就是一对多的关系
环境搭建:
导入lombok插件包 (简单代码)
===》配置mybatis-config核心配置文件
===》配置工具类MybatisUtils(里面涉及sqlsessionFactoryBuilder、sqlsessionFactory-sqlsession等)====》
pojo
student类
@Data public class Student { private int id; private String name; private int tid; }
Teacher类
@Data public class Teacher { private int id; private String name; //一个老师会有很多学生 集合关系 private List<Student> students; }
TeacherMapper.xml文件
按照结果嵌套查询(连表查询)
<select id="getTeacher" resultMap="TeacherToStudentMap"> select t.id tid,t.name tname,s.name sname ,s.id sid from teacher t,student s where t.id=s.tid and t.id=#{tid}; </select> <resultMap id="TeacherToStudentMap" type="Teacher" > <result property="id" column="tid" ></result> <result property="name" column="tname" ></result> <collection property="students" ofType="Student"> <result property="id" column="sid"></result> <result property="name" column="sname"/> <result property="tid" column="tid"/> </collection> </resultMap>
按照查询条件查询 (子查询)
<select id="getTeacher2" resultMap="TeacherToStudentMap2" > select * from teacher where id=#{tid2} </select> <resultMap id="TeacherToStudentMap2" type="Teacher" > <collection property="students" javaType="ArrayList" ofType="Student" column="id" select="getStudent"/> </resultMap> <select id="getStudent" resultType="Student"> select * from student where tid=#{tid2} </select>
- 关联 - association 【多对一】
- 集合 - collection 【一对多】
- javaType & ofType
- JavaType 用来指定实体类中属性的类型
- ofType 用来指定映射到List或者集合中的 pojo类型,泛型中的约束类型!
注意点:
- 保证SQL的可读性,尽量保证通俗易懂
- 注意一对多和多对一中,属性名和字段的问题!
- 如果问题不好排查错误,可以使用日志 , 建议使用 Log4j