概述
系列文章目录
MyBatis01:创建、运行、测试一个mybatis项目
MyBatis02:使用MyBatis查询数据
MyBatis03:嵌套查询、嵌套结果、延迟加载
MyBatis04:动态SQL
MyBatis05:类型转换器
MyBatis06:分页插件、MyBatis配置文件中的标签
MyBatis07:MyBatis注解
文章目录
- 系列文章目录
- 前言
- 一、ResultMap
- 1. 查询语句的执行过程
- 2. ResultMap的优势
- 3. ResultMap的作用
- 4. 数据类型
- 二、一对一,对象属性
- 1. 一对一,嵌套查询
- 2. 一对一,嵌套结果
- 三、一对多,集合属性
- 1. 一对多,嵌套查询
- 2. 一对多,嵌套结果
- 四、嵌套查询和嵌套结果的联系和区别
- 1. 嵌套结果
- 2. 嵌套查询
- 五、 延迟加载/懒加载
- 1. 作用
- 2. 如何配置懒加载
- 3. 案例说明
- 总结
前言
这篇文章是对查询结果ResultMap的进一学习。前面一篇文章的末尾,简单的介绍了resultType和resultMap的联系与区别。
一、ResultMap
1. 查询语句的执行过程
sql语句查询到结果后,将结果返回给resultMap,由resultMap创建对象。根据column和property的映射关系,获取数据库里字段的值,并将其赋给Java的属性。
2. ResultMap的优势
事实上对于一个复杂的交互代码,可能需要写上千行的代码来实现连接映射(join mapping)使用ResultMap的目的就是让我们只需要使用简单的配置语句,而不需要详细地处理结果映射。对更复杂的语句除了使用一些必须的语句描述外,就不需要做其他的处理了。
3. ResultMap的作用
将查询结果映射为对象,再把对象映射到集合里(因为不知道会查询到多少对象,所以需要将对象映射到集合里)。我们只需要对应好字段和属性即可。通过ResultMap建立数据库字段和Java属性的映射关系。
4. 数据类型
- javaType:实体属性的数据类型,可以省略
- jdbcType:数据库字段的数据类型,可以省略
通过mybatis框架的转化器,可以将数据库里的类型转化为Java程序类型
二、一对一,对象属性
背景:为学生的班级对象属性映射值
<sql id="base_info">id,name,sex,birthday,age,classid</sql>
<select id="selectByPrimaryKey" resultMap="baseMap">
select <include refid="base_info"></include> from student
where id = #{id}
</select>
一对一的查询语句就是通过某个参数,查询到某个对象
1. 一对一,嵌套查询
根据查询条件column,通过select查询语句将查询到的结果映射给property属性
<association property="clazz" column="classid" select="com.dao.ClazzMapper.selectByPrimaryKey"></association>
标签/属性 | 属性值 | 含义/作用 |
---|---|---|
association标签 | 为对象属性映射值 | |
property | clazz | 对象属性 |
column | classid | 作为查询条件的数据库字段 |
select | com.dao.ClazzMapper.selectByPrimaryKey | 调用方法进行查询 |
完整代码:
<resultMap id="baseMap2" type="com.bean.Student">
<id column="id" property="id"></id>
<result column="name" property="name"></result>
<result column="sex" property="sex"></result>
<result column="birthday" property="birthday"></result>
<result column="age" property="age"></result>
<result column="classid" property="classId"></result>
<association property="clazz" column="classid" select="com.mapper.ClazzMapper.selectByPrimaryKey"></association>
</resultMap>
<select id="selectStudentAndClazz" resultMap="baseMap2">
select s.*, c.classname from student s left join clazz c on s.classid = c.id where s.id = #{id}
</select>
2. 一对一,嵌套结果
分别建立对象属性和对象属性的属性的映射关系即可
<association property="clazz" javaType="com.bean.Clazz">
<!--将查询到的学生的classid赋值给班级的id-->
<id column="classid" property="id"></id>
<result column="classname" property="classname"></result>
</association>
标签/属性 | 属性值 | 含义/作用 |
---|---|---|
association标签 | 为对象属性映射值 | |
property | clazz | 对象属性 |
javaType | com.bean.Clazz | 对象属性的数据类型 |
id标签 | 用来设置主键 | |
result标签 | 用来设置其他字段 | |
column | classid | 数据库的字段 |
property | id | 对象属性的属性 |
完整代码:
<resultMap id="baseMap3" type="com.bean.Student">
<id column="id" property="id"></id>
<result column="name" property="name"></result>
<result column="sex" property="sex"></result>
<result column="birthday" property="birthday"></result>
<result column="age" property="age"></result>
<result column="classid" property="classId"></result>
<association property="clazz" javaType="com.bean.Clazz">
<id column="classid" property="id"></id>
<result column="classname" property="classname"></result>
</association>
</resultMap>
<select id="selectStudentAndClazz2" resultMap="baseMap3">
select s.*, c.classname from student s left join clazz c on s.classid = c.id where s.id = #{id}
</select>
这里是将从数据库中查询到的结果,赋值给Java属性。
三、一对多,集合属性
背景:为学生的成绩集合属性映射值
<select id="selectAll" resultMap="baseMap2">
select s.*, c.classname,sc.id scid, sc.score, sc.course, sc.examdate from student s left join clazz c on s.classid = c.id
LEFT JOIN scores sc ON s.id = sc.stuid
</select>
一对多的查询用到了多表联查,查询到的是多条数据。
1. 一对多,嵌套查询
根据查询条件column,通过select查询语句将查询到的结果映射给property属性
<collection property="scores" column="id" select="com.dao.ScoresMapper.selectByStuid"></collection>
标签/属性 | 属性值 | 含义/作用 |
---|---|---|
collection标签 | 为集合属性映射值 | |
property | scores | 集合属性 |
column | id | 作为查询条件的数据库字段 |
select | com.dao.ScoresMapper.selectByStuid | 调用方法进行查询 |
2. 一对多,嵌套结果
分别建立对象属性和对象属性的属性的映射关系即可
注意:当字段名冲突时,需要起别名
<collection property="scores" ofType="com.bean.Scores">
<id column="scid" property="id"></id>
<result column="score" property="score"></result>
<result column="course" property="course"></result>
<result column="examdate" property="examdate"></result>
</collection>
标签/属性 | 属性值 | 含义/作用 |
---|---|---|
collection标签 | 为集合属性映射 | |
property | scores | 指代集合属性 |
ofType | com.bean.Scores | 集合属性的数据类型 |
id标签 | 用来设置主键 | |
result标签 | 用来设置其他子段 | |
column | scid | 数据库字段 |
property | id | 集合属性的属性 |
四、嵌套查询和嵌套结果的联系和区别
1. 嵌套结果
嵌套结果是嵌套查询结果。
<resultMap id="baseMap" type="com.bean.Pet">
<id property="petId" column="petId"></id>
<result property="petName" column="petName"></result>
<result property="birthday" column="birthday"></result>
<result property="typeId" column="typeId"></result>
<!--javaType是Java数据类型-->
<association property="pettype" javaType="com.bean.Pettype">
<id property="typeId" column="typeId"></id>
<result property="typeName" column="typeName"></result>
</association>
<!--ofType是集合里的数据类型-->
<collection property="healhistorys" ofType="com.bean.Healhistory">
<id property="id" column="id"></id>
<result property="petId" column="petId"></result>
<result property="health" column="health"></result>
<result property="checkdate" column="checkdate"></result>
</collection>
</resultMap>
<select id="selectByPrimaryKey" resultMap="baseMap">
select p.*, pt.*, h.id,h.petId hpetId, h.health, h.checkdate from pet p
left join pettype pt on p.typeId = pt.typeId
left join healhistory h on p.petId = h.petId
where p.petId = #{petId}
</select>
嵌套结果使用的是多表联查,所有字段都需要查出来,然后根据映射关系一一进行映射。需要注意,当列名相同时,需要起别名来防止字段冲突。
2. 嵌套查询
嵌套查询是嵌套查询语句。
<resultMap id="baseMap2" type="com.bean.Pet">
<id property="petId" column="petId"></id>
<result property="petName" column="petName"></result>
<result property="birthday" column="birthday"></result>
<result property="typeId" column="typeId"></result>
<association property="pettype" column="typeId" select="com.dao.PettypeMapper.selectByPrimaryKey"></association>
<collection property="healhistorys" column="petId" select="com.dao.HealhistoryMapper.selectByPetid"></collection>
</resultMap>
<select id="selectAll" resultMap="baseMap2">
select * from pet
</select>
嵌套查询使用的是单表查询,对象属性和集合属性通过调用自己的映射的查询方法来获取的。
优点:查询语句简单,与相关子查询相似,但比相关子查询效率高,因为带缓存。
嵌套查询可以添加懒加载,只有使用到对应的属性才会执行相应的查询,否则就不会执行对应的查询语句。
五、 延迟加载/懒加载
作用于嵌套查询
1. 作用
有时候我们在查询数据时,要查询的数据不需要包含对象属性或集合属性时,我们该怎么查询?我们可以单独设置一个返回值类型,在获取返回值的时候不添加对象属性或集合属性,这样就不会获取到对象属性和集合属性了。但如果我们不单独添加这样一个返回值类型,而是在原有的返回值类型包含对象属性和集合属性的情况下,如何实现可以在不查询对象属性和集合属性的时候不加载对象属性和集合属性,只有在查询对象属性和集合属性的时候才加载对象属性和集合属性。如果使用的是嵌套查询,这时就可以使用延迟加载。在设置延迟加载/懒加载后,可以极大的提高查询效率。在不需要查询对象属性和集合属性的时候,程序就不会执行对象属性和集合属性相关的查询语句。只有在指定要查询的对象和集合后,才会查询对应的对象和属性。
2. 如何配置懒加载
在MyBatis的主配置文件中为ResultMap映射的对象属性和集合属性一起做配置,添加如下配置语句。
3. 案例说明
-
不添加延迟加载时,如果我们使用嵌套查询查询普通属性时,程序也会查询对象属性和集合属性,这样就会导致查询效率较低。
-
当我们添加延迟加载后,当我们只查询普通属性时,就不会查询成员属性和集合属性
-
添加延迟加载后,只有当我们查询成员属性和集合属性时,才会执行相应的查询语句
总结
今天,主要学了ResultMap如何为对象属性和集合属性设置返回值的映射。可以通过嵌套查询和嵌套结果两种方式来实现,这里分别介绍了嵌套查询和嵌套结果用到的标签和属性,主要是明确如何使用。最后还介绍了RresultMap的延迟加载,如何配置,以及延迟加载的优点。
最后
以上就是想人陪戒指为你收集整理的MyBatis03:嵌套查询、嵌套结果、延迟加载系列文章目录前言一、ResultMap二、一对一,对象属性三、一对多,集合属性四、嵌套查询和嵌套结果的联系和区别五、 延迟加载/懒加载总结的全部内容,希望文章能够帮你解决MyBatis03:嵌套查询、嵌套结果、延迟加载系列文章目录前言一、ResultMap二、一对一,对象属性三、一对多,集合属性四、嵌套查询和嵌套结果的联系和区别五、 延迟加载/懒加载总结所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复