4.1 嵌套查询 vs 连接查询
sql不同:
连接查询:涉及多表连接, 当出现重复列时 需要对重复的列进行 列的重命名
嵌套查询: 就是单表查询
参与的mapper文件不同:
连接查询: 在一个mapper文件中 配置即可
嵌套查询: 需要 在 association或collection 中 通过 select 调用 另外的mapper
执行效率:
连接查询: 直接查询, 多表连接查
嵌套查询: 是 每执行一个Product 就会查一个Category
练习: emp 与 dept 的 一对一的嵌套查询
4.1 1对多 关联查询及嵌套查询
1对1 或 1对多 都是 ResultMap的配置
1. 1对多 关联查询(连接查询) 基本是 90%与 一对一 关联查询类似
product 与 category
一个 product 属于 一个 category
Product.java 增加 Category cate 属性
一个 category 可以包含多个 product
a. 修改 Category.java 增加 一个 List<Product> proList 属性
b. 修改 查询方法
CategoryMapper.java
修改 findAll() 方法, 进行 查询 类别时 显示 该类别下的product
c. 修改 CategoryMapper.xml
为 resultMap 增加 collection 子标签
collection 需要 配置 property 及 ofType
property : 指 实体中的属性名, 区分大小写
ofType: 需要写 property 对应的属性的类型, 如果是 List 多个,则写一个
注意事项: 如果 sql 中 存在重复列, 记得 必须将列进行 重命名
配置一对多 使用 collection ,必须配置 property 及 ofType
package entity;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.ToString;
import java.util.List;
/**
* 实体层-- 与数据库的表 进行 映射
*
*/
@AllArgsConstructor
@NoArgsConstructor
@Data
@ToString
public class Category {
private int cno;// 类别编号
private String name;//类别名称 注意 数据库表 category中 使用的是 cname
// 1对多
private List<Product> proList;
}
package entity;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.ToString;
/**
*
* 实体层 :
* 无参构造
* 全参构造
* 每个属性 get/set
* 重写toString()
*
* 因为在pom.xmlzhong 增加了 lombok.jar
*
* 因此 以上内容 采用 注解实现
*/
@ToString //重写 同String()
@NoArgsConstructor //无参构造
@AllArgsConstructor //全参构造
@Data //get/set
public class Product {
private int id;//id
private String titleInfo;//title
private double oldPrice;//oldprice
private double p; //price
private int cateId;// cid
private int rate;//rate
private String url;
private Category cate; //一对一,
}
package mapper;
import entity.Category;
import java.util.List;
public interface CategoryMapper {
/**
* 查询全部类别信息
* @return
*/
List<Category> findAll();
/**
* 按照主键id进行查询
* @param id
* @return
*/
Category findById(int id);
}
<?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="mapper.CategoryMapper">
<!-- 方法1: 当 属性与列名不一致时, 使用 对列进行 重命名-->
<!--<select id="findAll" resultType="Category">
select id as cno,cname name from category
</select>-->
<!--声明一个resultMap
表 category 包含 id,cname
类 Category 包含 cno,name
-->
<!--方法2: 使用resultMap 来解决 属性与列名不一致的问题-->
<resultMap id="categoryMap" type="Category">
<id property="cno" column="cno"/>
<result property="name" column="cname"/>
<!--配置 1对多 -->
<collection property="proList" ofType="Product">
<id property="id" column="id"/>
<result property="titleInfo" column="title"/>
<result property="oldPrice" column="oldprice"/>
<result property="p" column="price"/>
<result property="cateId" column="cid"/>
<result property="rate" column="rate"/>
<result property="url" column="imgurl"/>
</collection>
</resultMap>
<select id="findAll" resultMap="categoryMap">
select c.id cno,c.cname,p.*
from category c,product p
where c.id = p.cid
</select>
<select id="findById" parameterType="int" resultMap="categoryMap">
select * from category where id=#{id}
</select>
</mapper>
@Test
public void testFindAll(){
CategoryMapper mapper = session.getMapper(CategoryMapper.class);
List<Category> list = mapper.findAll();
for(Category c:list){
System.out.println(c.getName()+"包含以下 商品");
for(Product p:c.getProList()){
System.out.println(p.getTitleInfo()+"----"+p.getP());
}
}
}

本文详细介绍了MyBatis中嵌套查询与连接查询的区别,涉及一对一和一对多关联,如何在Entity和Mapper中配置以及处理重复列问题,重点展示了ResultMap在配置一对多关联时的使用方法。

3233

被折叠的 条评论
为什么被折叠?



