Mabtis基础之【多对一】【一对多】【多对多】关系XMLl形式简述


分类和产品的一对多关系

Category实体类,提供products的集合

List<Product> products;

通过left join关联查询,对Category和Product表进行关联查询。
与前面学习的有所区别,这里不是用的resultType, 而是resultMap,通过resultMap把数据取出来放在对应的 对象属性里
注: Category的id 字段 和Product的id字段同名,Mybatis不知道谁是谁的,所以需要通过取别名cid,pid来区分。
name字段同理。

<?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.how2java.pojo">
        <resultMap type="Category" id="categoryBean">
            <id column="cid" property="id" />
            <result column="cname" property="name" />

            <!-- 一对多的关系 -->
            <!-- property: 指的是集合属性的值, ofType:指的是集合中元素的类型 -->
            <collection property="products" ofType="Product">
                <id column="pid" property="id" />
                <result column="pname" property="name" />
                <result column="price" property="price" />
            </collection>
        </resultMap>

        <!-- 关联查询分类和产品表 -->
        <select id="listCategory" resultMap="categoryBean">
            select c.*, p.*, c.id 'cid', p.id 'pid', c.name 'cname', p.name 'pname' 
            from category_ c 
            left join product_ p on c.id = p.cid
        </select>   
    </mapper>



产品和分类的多对一关系

为Product增加category属性

private Category category;

提供Product.xml,通过listProduct配置关联查询的sql语句。
然后通过resultMap ,进行字段和属性的对应。
使用association 进行多对一关系关联,指定表字段名称与对象属性名称的一一对应关系
注: Category的id 字段 和Product的id字段同名,Mybatis不知道谁是谁的,所以需要通过取别名cid,pid来区分。
name字段同理。

<?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.how2java.pojo">
        <resultMap type="Product" id="productBean">
            <id column="pid" property="id" />
            <result column="pname" property="name" />
            <result column="price" property="price" />

            <!-- 多对一的关系 -->
            <!-- property: 指的是属性名称, javaType:指的是属性的类型 -->
            <association property="category" javaType="Category">
                <id column="cid" property="id"/>
                <result column="cname" property="name"/>
            </association>
        </resultMap>

        <!-- 根据id查询Product, 关联将Orders查询出来 -->
        <select id="listProduct" resultMap="productBean">
            select c.*, p.*, c.id 'cid', p.id 'pid', c.name 'cname', p.name 'pname' 
            from category_ c 
            left join product_ p on c.id = p.cid
        </select>   
    </mapper>



订单Order和产品Product的多对多关系

一张订单里 可以包含多种产品
一种产品 可以出现在多张订单里
这就是多对多关系
为了维系多对多关系,必须要一个中间表(hibernate也是一样的)。 在这里我们使用订单项(OrderItem)表来作为中间表


实体类OrderItem(维护表)字段如下:

private int id;
private int number;
private Order order;
private Product product;

本文只在Order角度观察
实体类Order字段如下:

private int id;
private String code;
List<OrderItem> orderItems;

Order.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.how2java.pojo">

        <!-- 联合order_, order_item_, product_ 三张表进行查询 -->
        <!-- 查询结果 id和code字段放在Order对象里 -->
        <resultMap type="Order" id="orderBean">
            <id column="oid" property="id" />
            <result column="code" property="code" />

            <!-- 然后通过一对多的<collection>标签把oiid和number放在OrderItem对象里(不包括自身在维护表中的字段order) -->
            <collection property="orderItems" ofType="OrderItem">
                <id column="oiid" property="id" />
                <result column="number" property="number" />    

                <!-- 最后把pid,pname,price放进Product对象里 --> 
                <association property="product" javaType="Product">
                    <id column="pid" property="id"/>
                    <result column="pname" property="name"/>
                    <result column="price" property="price"/>
                </association>
            </collection>   
        </resultMap>

        <sql id="test">
            select o.*,p.*,oi.*, o.id 'oid', p.id 'pid', oi.id 'oiid', p.name 'pname' 
                from order_ o 
                left join order_item_ oi on o.id =oi.oid 
                left join product_ p on p.id = oi.pid
        </sql>

        <select id="listOrder" resultMap="orderBean">
            <include refid="test"></include> 
        </select>

        <select id="getOrder" resultMap="orderBean">
            <include refid="test"></include> 
            where o.id = #{id} 
        </select>
    </mapper>

后续就可以进行:查询多对多关系,建立多对多关系,删除多对多关系操作。




【扩展】还可以重用嵌套对象(一般情况下很少):
association是嵌套查询中最简单的一种情况,一般我们都会用一个Car对面包含所有的属性,这里的例子使用了嵌套对象,使对像的结构更鲜明。不过一般情况下很少会拆分一个对象为多个,用的多的时候是多表查询的嵌套。


<mapper namespace="org.apache.ibatis.submitted.associationtest.Mapper">

    <resultMap type="org.apache.ibatis.submitted.associationtest.Car" id="carResult">
        <id column="carid" property="id"/>
        <result column="cartype" property="type"/>
        <association property="engine" resultMap="engineResult"/>
        <association property="brakes" resultMap="brakesResult"/>
    </resultMap>
    <resultMap type="org.apache.ibatis.submitted.associationtest.Engine" id="engineResult">
        <result column="enginetype" property="type"/>
        <result column="enginecylinders" property="cylinders"/>
    </resultMap>
    <resultMap type="org.apache.ibatis.submitted.associationtest.Brakes" id="brakesResult">
        <result column="brakesType" property="type"/>
    </resultMap>

    <select id="getCars" resultMap="carResult">
    select * from cars
  </select>

    <select id="getCarsNonUnique" resultMap="carResult">
    select 1 as carid, cartype, enginetype, enginecylinders, brakestype from cars
  </select>

    <select id="getCars2" resultMap="carResult">
    select 1 as carid, cartype, enginetype, enginecylinders, brakestype from cars where carid in (1,2)
  </select>




参考来源:
http://how2j.cn/k/mybatis/mybatis-many-to-many/1091.html#nowhere
https://blog.csdn.net/isea533/article/details/20868189

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值