Mybatis-多表联查

news2024/9/28 11:20:59

多表联查

  • 一、步骤一:创建pojo实体类
  • 二、步骤二:明确两个实体类之间的关系
  • 三、步骤三:修改pojo实体类
  • 四、步骤四:编写Mapper接口
  • 五、步骤五:编写Mapper映射文件
      • 题目1:通过订单id查询订单详情以及所属用户
      • 题目2:通过用户id查询用户信息以及她所有的订单
  • 六、补充

在数据库查询中,很多时候不只是查询一张表,而是需要将多张表结合起来才能获得需要的数据,下面介绍在mybatis中怎么实现多表联查(前提是所有的依赖均已配置完成)

一、步骤一:创建pojo实体类

将需要用到的表全部创建成java的实体类,导入lombok依赖(自动生成get、set等方法)
User 用户表 Order 订单表

@Data
public class User {
    private Integer ID;
    private String username;
    private String PASSWORD;
    private String sex;
    private Date brithday;
    private String address;
}

二、步骤二:明确两个实体类之间的关系

一个用户可以有多条订单,而一条订单只属于一个用户
所以;:用户对订单是1对多的关系
 
在设计数据库时(黄色部分):在多的一方(tb_order)中添加一个外键,与tb_user的主键对应(图中为uid)
 
在设计java对象时(红色部分): 需要根据题目进行pojo类的编写(具体看步骤三)

在这里插入图片描述


三、步骤三:修改pojo实体类

先分析清楚题目 如:

①:根据id查询订单以及订单的所属用户信息
=> 返回的数据是tb_order表中的数据+tb_user表中的数据,需要修改的实体类是Order,因为是根据order的id查询的


//需要在Order的实体类中引入User对象
public class Order {
    private Integer id;
    private Integer userid;
    private Date createtime;
    private String state;

//    多对一
    private User user = new User();
}

②:根据用户id查询她的各类订单
=>返回的数据是tb_user+tb_order表中的数据,但是不同与上面的是:由于订单有多条所以订单需要用集合来装,而查询出的数据是要根据用户的id查询所有需要修改User类

// 需要在User表中的实体类中引入数据类型为Order的集合
public class User implements Serializable {
    private Integer ID;
    private String username;
    private String PASSWORD;
    private String sex;
    private Date brithday;
    private String address;

//    一对多
    private List<Order> orders = new ArrayList<>();
}


四、步骤四:编写Mapper接口

public interface UserMapper {
//    通过订单id查询订单详情以及所属用户
    Order selectOrderAndInfoById(@Param("oid") int id);
//    通过用户id查询该用户的所有订单
    User selectByUserIdForOrder(@Param("uid") int id);
//    根据id查询用户
    User selectUserByid(@Param("uid") int id);
}

五、步骤五:编写Mapper映射文件

需要指定该映射文件是步骤四的Mapper,在namespace中指定

重点来了:

题目1:通过订单id查询订单详情以及所属用户

需要知道的是我们关联的是两张表,如果直接用下面的sql语句则只能查出订单的信息而订单所属用户则为空,这是因为在执行过程中Order会自动映射到tb_order的内容,但是在Order表中定义的User对象则无法自动映射到tb_user表中的内容

SELECT  u.ID ,u.username,u.PASSWORD,u.sex,u.brithday,u.address,o.id oid,o.userid,o.createtime,o.state
FROM tb_user u JOIN tb_order o
ON u.ID  = o.userid
WHERE u.id= #{uid}

所以我们得手动映射User类,需要使用到resultMap
总体代码如下:

 <!--  todo  根据id查询订单以及对应的用户 -->
    <sql id="selectById">
        u.ID ,u.username,u.PASSWORD,u.sex,u.brithday,u.address,
        o.id oid,o.userid,o.createtime,o.state
    </sql>
    <resultMap id="selectParent" type="Order">
        <id property="id" column="oid"/>
        <result property="userid" column="userid"/>
        <result property="createtime" column="createtime"/>
        <result property="state" column="state"/>
    </resultMap>
    <resultMap id="selectChildren" type="Order" extends="selectParent">
        <association property="user" javaType="User" select="selectUserByid" column="userid"/>
    </resultMap>
    <select id="selectOrderAndInfoById" resultMap="selectChildren">
        SELECT
        <include refid="selectById"/>
        FROM tb_user u JOIN tb_order o
        ON u.ID = o.userid
        WHERE o.id = #{oid}
    </select>

    <!--    根据id查询用户-->
    <select id="selectUserByid" resultType="User">
        SELECT * FROM tb_user WHERE ID = #{uid}
    </select>

selectParent为手动映射的Order类的Map,selectChildren为手动映射的User类的Map,由于需要返回的订单类的数据所有type中填写Order类,children继承了parent那么children中也会有parent的映射,所有selectChildren的map中就有了Order+User的映射
在这里插入图片描述
这个时候再<select>标签resultMap中只需要传入selectChildren就可以了

<association property="user" javaType="User" select="selectUserByid" column="userid"/>

association :因为在Order类中的User对象是个,所以使用该关键字
property:对应Order表中的创建的User对象名
javaType:property对应的数据类型
select:就是指映射user对象去改方法中找,刚刚selectUserByid方法返回的就是一个User对象,这样就免去了手动一 一映射的麻烦
column:但是selectUserByid需要传入一个参数,这里传入的userid是从Order中查询得到的然后再传给该方法去查询对应的User


题目2:通过用户id查询用户信息以及她所有的订单

学会了上面的知识后,这里就只是发生了一点点的变化

同样也是,是根据用户的id查询所以需要在User类中进行操作,而一个用户有多条订单,所以需要在用户类User中定义一个Order类型的集合,mybatis也只能映射User类和tb_user表,无法映射Order类和tb_order表,所以我们也需要手动映射

总体代码如下:

 <!--    todo 根据用户id查询订单 -->

    <resultMap id="Userparent" type="User">
        <id column="ID" property="ID"/>
        <result column="username" property="username"/>
        <result column="PASSWORD" property="PASSWORD" />
        <result column="sex" property="sex" />
        <result column="brithday" property="brithday" />
        <result column="address" property="address" />

        <collection property="orders" ofType="Order" >
            <id column="oid" property="id"/>
            <result column="userid" property="userid"/>
            <result column="createtime" property="createtime"/>
            <result column="state" property="state" />
        </collection>

    </resultMap>
    <select id="selectByUserIdForOrder" resultMap="Userparent" parameterType="int">
        SELECT <include refid="selectById"/>
        FROM tb_user u JOIN tb_order o
        ON u.ID  = o.userid
        WHERE u.id= #{uid}
    </select>

与上面不同的是集合映射使用关键字collection ,并且返回类型不再使用type而是使用ofType来指定
前面题目一映射是使用的继承,现在题目二映射是直接在父映射中继续映射,并且没有使用方法


六、补充

id唯一标识符
type写返回的类的类名
<result/>对非主键的映射
<id/>对主键的映射
property关联属性名 也就是User类中定义的各属性
column关联属数据库的字段
javaType关联属性的数据类型 在集合属性时不要写,但是在题目一的情况下就需要使用
ofType关联属性的数据类型 在集合属性时写,但是在题目一的情况下就不要使用

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/55846.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

OpenCV入门(C++/Python)- 使用OpenCV读取、显示和写入图像(一)

使用OpenCV读取、显示和写入图像1.imread()读取图像imread()函数2.imshow()在窗口中显示图像waitKey()destoryAllWindows()3.imwrite()将图像写入文件目录读取、显示和写入图像是图像处理和计算机视觉的基础。即使裁剪、调整大小、旋转或应用不同的过滤器来处理图像&#xff0c…

C. Carrying Conundrum(思维 + 奇偶数位)

Problem - 1567C - Codeforces 爱丽丝刚刚学会了加法。但是&#xff0c;她还没有完全学会 "携带 "的概念--她不是携带到下一列&#xff0c;而是携带到左边两列的列。 例如&#xff0c;评估20392976这个和的常规方法是如图所示。 然而&#xff0c;爱丽丝是按照图中的…

【在SpringBoot项目中使用Validation框架检查数据格式-常用的检查注解】

常用的检查注解 使用Validation框架检查数据格式时&#xff0c;常用的检查注解有&#xff1a; NotNull&#xff1a;不允许为null值 可用于任何类型的参数NotEmpty&#xff1a;不允许为空字符串&#xff0c;即长度为0的字符串 仅用于检查字符串类型的参数NotBlank&#xff1a;不…

【D3.js】1.17-给 D3 元素添加标签

title: 【D3.js】1.17-给 D3 元素添加标签 date: 2022-12-02 14:35 tags: [JavaScript,CSS,HTML,D3.js,SVG] 为了让图更易懂&#xff0c;我们给每一个rect添加上标签。 一、学习目标 如何添加text元素&#xff1f; .append(“text”) 如何设置text元素的值&#xff1f; .attr(…

[附源码]计算机毕业设计在线图书销售系统Springboot程序

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

IPWorks macOS Edition通信组件

IPWorks macOS Edition通信组件 用于Internet通信的一整套组件。 IPWorks是一个用于Internet开发的综合框架&#xff0c;它消除了Internet开发的复杂性&#xff0c;提供了可编程的、支持SSL的组件&#xff0c;以便于执行诸如确保安全、发送电子邮件、传输文件、管理网络、浏览W…

物联网 MQTT 协议

MQTT官网&#xff1a;MQTT - The Standard for IoT Messaging MQTT中文网&#xff08;全是广告&#xff09;&#xff1a;首页 | MQTT中文网 物联网百科 物联网&#xff08;Internet of Things&#xff0c;简称IoT&#xff09;是指通过各种信息传感器、射频识别技术、全球定位…

在线编程教学技术解决方案,覆盖所有授课场景需求

在线编程教学是一种应用较为广泛的远程教学形式&#xff0c;例如&#xff1a;互动体验&#xff0c;音视频技术的普及&#xff0c;对线上教学的质量与学习效率带来了很大的提升。在线编程教学可以让教师对学生进行在线编程教学&#xff0c;以一对多小班教学为主。那么在线编程教…

线上项目源码安全性处理方案

场景&#xff1a; 最近项目提出要对线上代码进行安全性处理&#xff0c;防止客户直接通过反编译工具将代码反编译出来 方案&#xff1a; 第一种方案使用的是代码混淆 第二种方案使用的是代码加密 方案比较 方案一&#xff1a;采用的proguard-maven-plugin插件 方案二&#xf…

要花多少亿美元,HPE才能买下超融合鼻祖Nu­t­a­n­ix?

【全球存储观察 | 热点关注】据报道&#xff0c;慧与科技HPE在近几个月与超融合提供商Nutanix就收购进行了谈判。 在这之前的2017年2月&#xff0c;HPE以6.5亿美元收购了超融合全球老二SimpliVity&#xff0c;后来整合成了HPE重要的超融合产品线&#xff0c;并进一步丰富了整体…

Seal库官方示例(五):ckks_basics.cpp解析

这个代码计算的是πx30.4x1\pi \times x^30.4 \times x 1πx30.4x1。 代码解析 方案选择 首先照例是方案选择 EncryptionParameters parms(scheme_type::ckks);参数设置 CKKS方案中使用rescale方法来控制膨胀的密文规模和噪声&#xff0c;这个和modulus switching有点类似…

[激光原理与应用-28]:《激光原理与技术》-14- 激光产生技术 - 激光的主要参数与指标

目录 1、 激光器的门限电流与功率输出 2、激光器的调制增益 3、功率/能量密度 6、额定功耗 7、转换效率 8、光斑大小 9、线宽 10、激光器的谱线宽度。 11、激光器的相对强度噪声RIN。 12、激光器的线性范围。 13、带内平坦度 14、激光器的温度特性 15、激光器的交…

基于PHP+MySQL信息技术学习网站设计与实现

智多在线网络学习平台为学习各种技术查看资料的用户提供一个准确、最新的技术与相关文档&#xff0c;浏览目前流行教学的新闻&#xff0c;提出技术上遇到的难点及问题&#xff0c;帮助其他用户回答所提出的问题&#xff0c;上传想要分享的资源&#xff0c;下载要获取的相关技术…

Spirng MVC——获取参数详解

文章目录1. 什么是 Spirng MVC1.1 MVC 定义1.2 MVC 和 Spring MVC 的关系2. 创建Spring MVC 项目3. Spring MVC 学习目标3.1 实现用户和程序的映射方法1&#xff1a;RequestMapping("/xxx")方法2&#xff1a;使用 POSTMapping("/xxx")方法3&#xff1a;使用…

Kali生成windows木马程序

目录 一、生成windows执行木马程序 二、进入msfconsole进行监听目标上线 三、目标运行木马和后渗透 四、问题 Meterpreter session 2 closed. Reason: Died 一、生成windows执行木马程序 -p windows/x64/meterpreter/reverse_tcp //载入64位payload攻击载荷&#xff0c…

RabbitMQ-惰性队列

文章目录1 消息堆积问题2 惰性队列2.1 基于命令行设置lazy-queue2.2 基于Bean声明LazyQueue(推荐)2.3 基于RabbitListener声明LazyQueue3 总结3.1 消息堆积问题的解决方案&#xff1f;3.2 惰性队列的优点有哪些&#xff1f;3.3 惰性队列的缺点有哪些&#xff1f;1 消息堆积问题…

BSA-maltose 牛血清白蛋白修饰麦芽糖 BSA-麦芽糖

产品名称&#xff1a;牛血清白蛋白修饰麦芽糖 英文名称&#xff1a;BSA-maltose 用途&#xff1a;科研 状态&#xff1a;固体/粉末/溶液 产品规格&#xff1a;1g/5g/10g 保存&#xff1a;冷藏 储藏条件&#xff1a;-20℃ 储存时间&#xff1a;1年 牛血清中的简单蛋白&#xff…

JAVA数据类型与变量

JAVA初阶 背景了解 Java语言之父—>高斯林。现代计算机之父—>冯诺依曼。 Java当中的main方法。 .java ->编译javac xxx.java -> xxx.class[字节码文件&#xff1a;二进制文件]。java命令 运行java程序 public class HelloWorld {//m main psvm 出现之后回车即可…

Qt第二十七章:QWidget、QMainWindow自定义标题栏并自由移动缩放

前提&#xff1a;UI必須采用自适应布局。 自定义组件【直接CV】custom_components.py from PySide6 import QtGui, QtWidgets, QtCore from PySide6.QtCore import Qt, QSize, QRect from PySide6.QtWidgets import QPushButton, QLabel, QWidgetclass QCustomTitleBar:def _…

基于SpringBoot vue的茶叶商城平台源码和论文含支付宝沙箱支付

此项目是前后端分离的 后台项目:shop 前端项目:Vue-shop 后端项目启动步骤: 1.先把sql导入数据库 2.把后台项目导入编辑器 3.修改数据库配置 4.启动项目 前端项目启动步骤: 1.打开Vue-shop目录,在这个文件夹里面加入cmd目录窗口 2.运行启动vue项目目录(需先安装nodejs软件)…