Spring+MyBatis使用collection标签的两种使用方法

目录

项目场景:

实战操作:

1.创建菜单表

2.创建实体

3.创建Mapper

4.创建xml

属性描述:

效率比较:


项目场景:

本文说明了Spring Boot+MyBatis使用collection标签的两种使用方法

  1. 方法一: 关联查询

  2. 方法二: 嵌套select查询


实战操作:

1.创建菜单表

这里只创建一张表,树结构只有两级,方便学习,多表关联是同样的道理

c 复制代码
-- ----------------------------
-- Table structure for menu
-- ----------------------------
DROP TABLE IF EXISTS `menu`;
CREATE TABLE `menu`  (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL COMMENT '角色名称',
  `pid` int(3) NULL DEFAULT NULL COMMENT '0代表父级',
  `order` int(3) NULL DEFAULT NULL COMMENT '排序',
  PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 6 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_general_ci ROW_FORMAT = Dynamic;

-- ----------------------------
-- Records of menu
-- ----------------------------
INSERT INTO `menu` VALUES (1, '审核', 0, 1);
INSERT INTO `menu` VALUES (2, '栏目管理', 0, 2);
INSERT INTO `menu` VALUES (3, '应用审核', 1, 1);
INSERT INTO `menu` VALUES (4, '服务审核', 1, 2);
INSERT INTO `menu` VALUES (5, '角色管理', 2, 1);

2.创建实体

java 复制代码
package com.test.entity;

import lombok.Data;
import java.util.List;

@Data
public class Menu {

    private Integer id;
    private String name;
    private Integer pid;
    private Integer order;

    private List<Menu> menus;

}

3.创建Mapper

java 复制代码
package com.test.dao;

import com.test.entity.Menu;
import java.util.List;

public interface TestMapper{
    //关联查询
	List<Menu> selectMenu();
    //嵌套查询
	List<Menu> selectNestedMenu();
}

4.创建xml

XML 复制代码
<?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="com.test.dao.TestMapper">
    <!-- 公共字段 -->
    <resultMap id="BaseResultMap" type="com.test.entity.Menu">
        <result column="id" property="id"/>
        <result column="name" property="name"/>
        <result column="pid" property="pid"/>
        <result column="order" property="order"/>
    </resultMap>

    <!-- 方式一、关联查询:执行一次sql -->
    <!-- 定义resultMap -->
    <resultMap id="MenuResultMap" extends="BaseResultMap" type="com.test.entity.Menu">
        <!-- 关联集合映射,columnPrefix前缀,用于区分相同字段 -->
        <collection ofType="com.test.entity.Menu" resultMap="BaseResultMap" property="menus" columnPrefix="menu_">
        </collection>
    </resultMap>

    <!-- 查询语句 -->
    <select id="selectMenu" resultMap="MenuResultMap">
        select r.id ,r.name ,r.pid ,r.order ,
               r1.id AS menu_id ,r1.name AS menu_name ,r1.pid AS menu_pid,r1.order AS menu_order
        FROM menu r
        LEFT JOIN menu r1 ON r.id = r1.pid
        where r.pid=0
        order by r.order,r1.order
    </select>

    <!-- 方式二、嵌套查询:会执行多次sql -->
    <!-- 定义resultMap -->
    <resultMap id="NestedResultMap" extends="BaseResultMap" type="com.test.entity.Menu">
        <!-- 嵌套查询集合映射 -->
        <collection property="menus" column="id" select="selectChildMenu"/>
    </resultMap>

    <!-- 查询所有父级语句 -->
    <select id="selectNestedMenu" resultMap="NestedResultMap">
        select r.id ,r.name ,r.pid ,r.order
        FROM menu r
        where r.pid=0
        order by r.order
    </select>

    <!-- 查询下级 -->
    <select id="selectChildMenu" resultMap="BaseResultMap">
        select r.id ,r.name ,r.pid ,r.order
        FROM menu r
        where r.pid=#{id}
        order by r.order
    </select>

</mapper>

属性描述:

|--------------|---------------------------------------------------------------------------|
| 属性 | 描述 |
| property | 属性名:映射实体类属性名 |
| ofType | 映射集合的类型(指定一对多的集合里面元素的类型) |
| column | 映射数据库字段名,传多个 {"属性名"="参数","属性名"="参数"} |
| select | 用于加载复杂类型属性的映射语句的ID(它会从column 属性指定的列中检索数据,作为参数传递给目标 select 语句) |
| columnPrefix | 给关联的数据库中的 column 添加一个前缀(如果不添加前缀,当 两个表同时有 id 字段,查询结果时一定会产生覆盖,使得两个 id 的值一样) |


效率比较:

方法一(关联查询):只需要执行一次sql语句。

方法二(嵌套select查询):需要执行多次sql语句。

方法一比方法二的效率要高,但是在使用的时候,方法二的代码可重用性要高

比如:这里用的是菜单表,数据量不会太大,可以选择方法二(嵌套select查询)

源码: https://download.csdn.net/download/u011974797/88305627

相关推荐
ChinaRainbowSea1 小时前
十三,Spring Boot 中注入 Servlet,Filter,Listener
java·spring boot·spring·servlet·web
小游鱼KF1 小时前
Spring学习前置知识
java·学习·spring
二十雨辰1 小时前
[苍穹外卖]-12Apache POI入门与实战
java·spring boot·mybatis
阿乾之铭2 小时前
spring MVC 拦截器
java·spring·mvc
小电玩2 小时前
谈谈你对Spring的理解
java·数据库·spring
Amagi.3 小时前
Redis的内存淘汰策略
数据库·redis·mybatis
徐*红5 小时前
springboot使用minio(8.5.11)
java·spring boot·spring
哈喽,树先生7 小时前
1.Seata 1.5.2 seata-server搭建
spring·springcloud
执键行天涯7 小时前
【经验帖】JAVA中同方法,两次调用Mybatis,一次更新,一次查询,同一事务,第一次修改对第二次的可见性如何
java·数据库·mybatis