Mybatis的关联关系映射以及自定义resultMap三种映射关系

目录

经典面试题:

一,关联关系映射

二,具体步骤:

总结


前言:

今天我们来学习Mybatis的关联关系映射以及自定义resultMap三种映射关系,希望这篇博客可以帮助大家的学习工作!!!

 

经典面试题:

问 :在Mybatis中的表之间的关系是如何映射处理的?

答:

在MyBatis中,表与表之间的关系主要通过两种方式进行映射:一对一(One-to-One)和一对多(One-to-Many)关系。

对于一对一关系,可以使用两个表之间的外键进行映射。在MyBatis的映射文件中,可以使用<resultMap>标签定义一个结果映射对象,并使用<association>标签进行关联映射。

对于一对多关系,可以使用一个表的外键与另一个表的主键进行映射。在MyBatis的映射文件中,可以使用<resultMap>标签定义一个结果映射对象,并使用<collection>标签进行集合映射。

需要注意的是,在映射文件中,可以使用<resultMap>标签来定义表字段与Java对象属性之间的映射关系。

准备:将具有一对一,一对多的表导入mysqll数据库中去。

一,关联关系映射

关联关系映射在Mybatis中主要通过三种方式实现:一对一关联和一对多关联及多对多关联。

一,一对一

例如:一个用户(User)与一个地址(Address)之间的关系。

二,一对多

例如: 订单表的id对应多个订单详情表

三,多对多

例如:一本书对应多种类型,一种类型对应多本书

二,具体步骤:

一,一对一

2.1创建名为 t_hibernate_book (书籍表) 数据表

创建名为 t_hibernate_book_category (书籍类别表) 数据表 

其中名为 bid 的属性字段为 t_hibernate_book (书籍表) 的 bid(主键) 的外键

其中名为 cid 的属性字段为 t_hibernate_category (类别表) 的 category_id (主键) 的外键

创建名为 t_hibernate_category (类别表) 数据表 

 

t_hibernate_order (订单表) 数据表

 t_hibernate_order_item (订单详情表) 数据表

修改 generatorConfig.xml 的配置文件 

 

代码:

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE generatorConfiguration PUBLIC "-//mybatis.org//DTD MyBatis Generator Configuration 1.0//EN""http://mybatis.org/dtd/mybatis-generator-config_1_0.dtd" >
<generatorConfiguration><!-- 引入配置文件 --><properties resource="jdbc.properties"/><!--指定数据库jdbc驱动jar包的位置--><classPathEntry location="D:\\temp\\mvn_repository\\mysql\\mysql-connector-java\\5.1.44\\mysql-connector-java-5.1.44.jar"/><!-- 一个数据库一个context --><context id="infoGuardian"><!-- 注释 --><commentGenerator><property name="suppressAllComments" value="true"/><!-- 是否取消注释 --><property name="suppressDate" value="true"/> <!-- 是否生成注释代时间戳 --></commentGenerator><!-- jdbc连接 --><jdbcConnection driverClass="${jdbc.driver}"connectionURL="${jdbc.url}" userId="${jdbc.username}" password="${jdbc.password}"/><!-- 类型转换 --><javaTypeResolver><!-- 是否使用bigDecimal, false可自动转化以下类型(Long, Integer, Short, etc.) --><property name="forceBigDecimals" value="false"/></javaTypeResolver><!-- 01 指定javaBean生成的位置 --><!-- targetPackage:指定生成的model生成所在的包名 --><!-- targetProject:指定在该项目下所在的路径  --><javaModelGenerator targetPackage="com.CloudJun.model"targetProject="src/main/java"><!-- 是否允许子包,即targetPackage.schemaName.tableName --><property name="enableSubPackages" value="false"/><!-- 是否对model添加构造函数 --><property name="constructorBased" value="true"/><!-- 是否针对string类型的字段在set的时候进行trim调用 --><property name="trimStrings" value="false"/><!-- 建立的Model对象是否 不可改变  即生成的Model对象不会有 setter方法,只有构造方法 --><property name="immutable" value="false"/></javaModelGenerator><!-- 02 指定sql映射文件生成的位置 --><sqlMapGenerator targetPackage="com.CloudJun.mapper"targetProject="src/main/java"><!-- 是否允许子包,即targetPackage.schemaName.tableName --><property name="enableSubPackages" value="false"/></sqlMapGenerator><!-- 03 生成XxxMapper接口 --><!-- type="ANNOTATEDMAPPER",生成Java Model 和基于注解的Mapper对象 --><!-- type="MIXEDMAPPER",生成基于注解的Java Model 和相应的Mapper对象 --><!-- type="XMLMAPPER",生成SQLMap XML文件和独立的Mapper接口 --><javaClientGenerator targetPackage="com.CloudJun.mapper"targetProject="src/main/java" type="XMLMAPPER"><!-- 是否在当前路径下新加一层schema,false路径com.oop.eksp.user.model, true:com.oop.eksp.user.model.[schemaName] --><property name="enableSubPackages" value="false"/></javaClientGenerator><!-- 配置表信息 --><!-- schema即为数据库名 --><!-- tableName为对应的数据库表 --><!-- domainObjectName是要生成的实体类 --><!-- enable*ByExample是否生成 example类 --><!--<table schema="" tableName="t_book" domainObjectName="Book"--><!--enableCountByExample="false" enableDeleteByExample="false"--><!--enableSelectByExample="false" enableUpdateByExample="false">--><!--&lt;!&ndash; 忽略列,不生成bean 字段 &ndash;&gt;--><!--&lt;!&ndash; <ignoreColumn column="FRED" /> &ndash;&gt;--><!--&lt;!&ndash; 指定列的java数据类型 &ndash;&gt;--><!--&lt;!&ndash; <columnOverride column="LONG_VARCHAR_FIELD" jdbcType="VARCHAR" /> &ndash;&gt;--><!--</table>--><table schema="" tableName="t_hibernate_book" domainObjectName="HBook"enableCountByExample="false" enableDeleteByExample="false"enableSelectByExample="false" enableUpdateByExample="false"></table><table schema="" tableName="t_hibernate_category" domainObjectName="Category"enableCountByExample="false" enableDeleteByExample="false"enableSelectByExample="false" enableUpdateByExample="false"></table><table schema="" tableName="t_hibernate_book_category" domainObjectName="HBookCategory"enableCountByExample="false" enableDeleteByExample="false"enableSelectByExample="false" enableUpdateByExample="false"></table><table schema="" tableName="t_hibernate_order" domainObjectName="Order"enableCountByExample="false" enableDeleteByExample="false"enableSelectByExample="false" enableUpdateByExample="false"></table><table schema="" tableName="t_hibernate_order_item" domainObjectName="OrderItem"enableCountByExample="false" enableDeleteByExample="false"enableSelectByExample="false" enableUpdateByExample="false"></table></context>
</generatorConfiguration>

自动生成实体

创建一个 名为 OrderItemVo 的类,继承OrderItem类,及属性有Order对象

<!--  resultMap的映射--><resultMap id="OrderVoMap" type="com.lya.vo.OrderVo" ><result column="order_id" property="orderId"></result><result column="order_no" property="orderNo"></result><!--    一个对应多个--><collection property="orderItems" ofType="com.lya.model.OrderItem"><result column="order_id" property="orderId"></result><result column="order_no" property="orderNo"></result><result column="order_id" property="orderId"></result><result column="order_no" property="orderNo"></result></collection></resultMap><select id="byoid" resultMap=" " parameterType="java.lang.Integer" >select * from t_hibernate_order o ,t_hibernate_order_item ot where o.order_id = ot.oidand o.order_id = #{oid}</select>

在自动生成的 OrderItemMapper 接口中进行增加以下代码

 OrderItemVo selectByBiid(@Param("oiid") Integer oiid);

 

创建一个接口名为 : OrderItemBiz 接口

package com.lya.biz;import com.lya.vo.OrderItemVo;/*** @author 程序猿-小李哥* @site www.xiaolige.com* @company 猪八戒有限集团* @create 2023-09-04-9:38*/
public interface OrderItemBiz {OrderItemVo selectByBiid(Integer oiid);}

创建一个实现了名为 OrderItemBizImpl 

package com.lya.biz.impl;import com.lya.biz.OrderItemBiz;
import com.lya.mapper.OrderItemMapper;
import com.lya.model.OrderItem;
import com.lya.vo.OrderItemVo;
import org.springframework.beans.factory.annotation.Autowired;/*** @author 程序猿-小李哥* @site www.xiaolige.com* @company 猪八戒有限集团* @create 2023-09-04-9:40*/
public class OrderItemBizImpl implements OrderItemBiz {@Autowiredprivate OrderItemMapper orderItemMapper;@Overridepublic OrderItemVo selectByBiid(Integer oiid) {return orderItemMapper.selectByBiid(oiid);}
}

测试:

 

二,一对多

创建一个 名为 OrdeVo 的类,继承Order

package com.lya.vo;import com.lya.model.Order;
import com.lya.model.OrderItem;import java.util.ArrayList;
import java.util.List;/*** @author 程序猿-小李哥* @site www.xiaolige.com* @company 猪八戒有限集团* @create 2023-08-26-16:57*/
public class OrderVo extends Order {private List<OrderItem>  orderItems = new ArrayList<>();public List<OrderItem> getOrderItems() {return orderItems;}public void setOrderItems(List<OrderItem> orderItems) {this.orderItems = orderItems;}
}

在自动生成的 OrderMapper.xml 配置文件中增加以下配置

  <resultMap id="OrderVoMap" type="com.lya.vo.OrderVo"><result column="order_id" property="orderId" ></result><result column="order_no" property="orderNo" ></result><collection property="orderItems" ofType="com.lya.model.OrderItem"><result column="order_item_id" property="orderItemId" ></result><result column="product_id" property="productId" ></result><result column="quantity" property="quantity" ></result><result column="oid" property="oid" ></result></collection></resultMap><select id="selectByOid" resultMap="OrderVoMap" parameterType="java.lang.Integer" >SELECT * FROMt_hibernate_order o ,t_hibernate_order_item oiWHERE o.order_id = oi.oidAND o.order_id = #{oid}</select>

在自动生成的 OrderMapper接口中进行增加以下代码

OrderVo selectByOid(@Param("oid") Integer oid);

创建一个接口名为 : OrderBiz 接口

package com.lya.biz;import com.lya.vo.OrderVo;/*** @author 程序猿-小李哥* @site www.xiaolige.com* @company 猪八戒有限集团* @create 2023-09-04-10:04*/
public interface OrderBiz {OrderVo selectByOid(Integer oid);
}

创建一个实现类,名为 OrderBizImpl 

package com.lya.biz.impl;import com.lya.biz.OrderBiz;
import com.lya.mapper.OrderMapper;
import com.lya.vo.OrderVo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;/*** @author 程序猿-小李哥* @site www.xiaolige.com* @company 猪八戒有限集团* @create 2023-09-04-10:05*/
@Service
public class OrderBizImpl implements OrderBiz {@Autowiredprivate OrderMapper orderMapper;@Overridepublic OrderVo selectByOid(Integer oid) {return orderMapper.selectByOid(oid);}
}

测试:

    @Autowiredprivate OrderBiz orderBiz;@Testpublic void selectByOid() {OrderVo orderVo = orderBiz.selectByOid(7);System.out.println(orderVo);orderVo.getOrderItems().forEach(System.out::println);}

三,多对多

在自动生成的 HBookMapper.xml 配置文件中增加以下配置

  <resultMap id="HBookVoMap" type="com.lya.vo.HBookVo" ><result column="book_id" property="bookId"></result><result column="book_name" property="bookName"></result><result column="price" property="price"></result><collection property="categories" ofType="com.lya.model.Category"><result column="category_id" property="categoryId"></result><result column="category_name" property="categoryName"></result></collection></resultMap><select id="selectByBookId" resultMap="HBookVoMap" parameterType="java.lang.Integer" >SELECT * FROMt_hibernate_book b,t_hibernate_book_category bc ,t_hibernate_category cWHERE b.book_id = bc.bidAND bc.cid = c.category_idAND b.book_id = #{bid}</select>

在自动生成的 HBookMapper 接口 中增加以下方法

  HBookVo selectByBookId(@Param("bid") Integer bid);

创建一个接口名为 HBookBiz 

package com.lya.biz;import com.lya.vo.HBookVo;
import org.apache.ibatis.annotations.Param;/*** @author 程序猿-小李哥* @site www.xiaolige.com* @company 猪八戒有限集团* @create 2023-09-04-10:13*/
public interface HBookBiz {HBookVo selectByBookId(@Param("bid") Integer bid);}

创建一个实现类,名为 HBookBizImpl 

package com.lya.biz.impl;import com.lya.biz.HBookBiz;
import com.lya.mapper.HBookMapper;
import com.lya.vo.HBookVo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;/*** @author 程序猿-小李哥* @site www.xiaolige.com* @company 猪八戒有限集团* @create 2023-09-04-10:13*/
@Service
public class HBookBizImpl implements HBookBiz {@Autowiredprivate HBookMapper hBookMapper;@Overridepublic HBookVo selectByBookId(Integer bid) {return hBookMapper.selectByBookId(bid);}
}

测试

    @Autowiredprivate HBookBiz hbookBiz;@Testpublic void selectByBookId() {HBookVo hBookVo = hbookBiz.selectByBookId(8);System.out.println(hBookVo);hBookVo.getCategories().forEach(System.out::println);}

总结

学习Mybatis的关联关系映射可以带来以下收获和认识:

1. 数据库关系的抽象:学习MyBatis的关联关系映射可以有助于我们理解数据库中表与表之间的关系,如一对一和一对多关系。这可以提升我们对数据模型的理解和设计能力。

2. 对象关系映射(ORM)的学习:MyBatis采用了ORM的思想,通过映射配置将数据库表与Java对象进行关联。学习MyBatis的关联关系映射可以帮助我们掌握ORM的基本原理和实践技巧。

3. 数据库操作的灵活性:MyBatis的关联关系映射使得数据库操作更加灵活,能够方便地进行多表查询或关联查询。这有助于我们优化数据库访问性能,并提供更好的数据查询和操作能力。

4. 代码重用和维护性:通过MyBatis的关联关系映射,我们可以将一对一或一对多关系的查询逻辑封装成可复用的SQL语句或映射文件片段,提高代码的重用性和可维护性。

5. 高效的数据库访问:MyBatis的关联关系映射能够有效地利用数据库的连接和查询优化,减少不必要的数据库访问,提高数据库操作的效率。

这些收获和认识将帮助我们更好地应对实际项目中的数据库操作需求,并提升我们作为Java程序员的能力和竞争力。

 

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

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Jdk1.7之ConcurrentHashMap源码总结

文章目录 一、常见属性1. 初始化容量2. 加载因子3. 并发级别 二、重要方法1. 构造方法2. ConcurrentHashMap#put方法2.1 ConcurrentHashMap#put#ensureSegment2.2 ConcurrentHashMap#Segment#put2.2.1 Segment#put#scanAndLockForPut2.2.2 Segment#put#rehash 3. ConcurrentHas…

机器学习前沿:改进自身缺陷,满足新战略

前机械师&#xff08; 来源) 一、说明 机器学习在人工智能历史上扮演重要角色&#xff0c;然而&#xff0c;存在问题也不少。为了适应新时代和新任务&#xff0c;不做出重大改进是不可能的&#xff0c;本篇就一些突出问题和改进做出讨论。以便读者掌握未来的思路和方向。 二、机…

Spring5查缺补漏

Spring5-基础知识 笔记简介&#xff1a; 1、Spring概念 2、IOC 3、AOP 4、JDBCTemplate 5、事务管理 6、Spring5里边的新特性 概述&#xff1a; 1、Spring框架是一个轻量级 开源的javaEE框架。 轻量级&#xff1a;引入依赖的jar包数量少&#xff0c;体积小。不再需要…

【力扣每日一题】2023.9.9 课程表

目录 题目&#xff1a; 示例&#xff1a; 分析&#xff1a; 代码&#xff1a; 题目&#xff1a; 示例&#xff1a; 分析&#xff1a; 题目给我们一些课程的先修关系&#xff0c;也就是有些课我们需要先去学其他的课程才能学习&#xff0c;问我们是否可以学习完所有的课程。…

Qt 5.15集成Crypto++ 8.8.0(MSVC 2019)笔记

一、背景 笔者已介绍过在Qt 5.15.x中使用MinGW&#xff08;8.10版本&#xff09;编译并集成Crypto 8.8.0。 但是该编译出来的库&#xff08;.a和.dll&#xff09;不适用MSVC&#xff08;2019版本&#xff09;构建环境&#xff0c;需要重新编译&#xff08;.lib或和.dll&#xf…

pytorch(b站小土堆学习笔记P1-P15)

P3. Python学习中的两大法宝函数&#xff08;当然也可以用在PyTorch&#xff09; import torch#查看pytorch有哪些指令 print(dir(torch)) print(dir(torch.cuda)) #查看每条指令怎么用 help(torch.cuda.is_available) P4. PyCharm及Jupyter使用及对比 P5 dataset和dataloade…

MySQL 连接查询和存储过程

一、连接查询 mysql的连接查询&#xff0c;通常都是将来自两个或多个表的记录行结合起来&#xff0c;基于这些表之间的共同字段&#xff0c;进行数据的拼接 首先&#xff0c;要确定一个主表作为结果集&#xff0c;然后将其它表的行有选择性的连接到选定的主表结果上&#xff…

C动态分配

动态分布与静态发布&#xff1a; 静态分配 1、 在程序编译或运行过程中&#xff0c;按事先规定大小分配内存空间的分配方式。int a [10] 2、 必须事先知道所需空间的大小。 3、 分配在栈区或全局变量区&#xff0c;一般以数组的形式。 4、 按计划分配。 动态分配 1、在程序运…

企业架构LNMP学习笔记7

PHP介绍&#xff1a; HTML&#xff1a;超文本标记语言 http: 超文本传输协议 端口80 浏览器将html代码解析成web页面。 PHP&#xff1a;超文本预处理器。后端语言开发&#xff0c;页面上需要动态改变修改的&#xff0c;需要连接数据库查询数据&#xff0c;转为html。 主要…

3D印刷电路板在线渲染查看工具

从概念上讲&#xff0c;这是有道理的&#xff0c;因为PCB印制电路板上的走线从一个连接到下一个连接的路线基本上是平面的。 然而&#xff0c;我们生活在一个 3 维世界中&#xff0c;能够以这种方式可视化电路以及相应的组件&#xff0c;对于设计过程很有帮助。本文将介绍KiCad…

MDK-Keil AC6 Compiler屏蔽特定警告

最近在使用STM32CubeMX生成MDK工程是&#xff0c;使用了 AC6 版本的编译器进行编译代码&#xff0c;然后发现了一些警告&#xff0c;但是在 AC5 版本下编译又正常。于是研究了下怎么屏蔽特定的警告&#xff0c;这里记录一下。 1. Keil AC6屏蔽特定警告 遇到的警告如下&#x…

【计算机网络】HTTP(上)

文章目录 1.HTTP概念2. URLurlencode 和 urldecode转义规则 3. HTTP的宏观理解HTTP的请求HTTP的响应 4. 见一见HTTP请求和响应请求报头 1. 模拟一个简单的响应response响应报头 2. 从路径中获取内容ReadFile函数的实现 3.不同资源进行区分反序列化的实现ReadOneLine函数的实现P…