关联查询
- 一对一 是通过在任意一方的主键,引入对方主键作为外键来实现的,就是说主键与外键为同一字段
- 一对多 是通过在“多”的一方,添加“一”的一方的主键作为外键
- 多对多 是通过一张中间关系表,引入两张表的主键作为外键,两个主键成为联合主键或使用新的字段作为主键

-
user和orders:
User 与orders:一个用户可以创建多个订单,一对多 -
orders和orderdetail:
Orders 与 orderdetail:一个订单可以包括 多个订单明细,因为一个订单可以购买多个商品,每个商品的购买信息在orderdetail记录,一对多关系 -
orderdetail和items:
Orderdetail 与 items:多个订单明细只对应一个商品信息,多对一
一对一
需求:
根据商品ID查找定单信息,包括用户名和地址
一个订单对应一个用户
方法一:扩展类实现
-
在复杂查询时,单表对应的po类已经不能满足结果集的映射,所以根据需求建立一个扩展类作为resultType的类型
package com.hf.model; public class OrdersExt extends Orders { private String username; private String address; public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public String getAddress() { return address; } public void setAddress(String address) { this.address = address; } @Override public String toString() { return "OrdersExt{" + "username='" + username + '\'' + ", address='" + address + '\'' + '}'+super.toString(); } } -
声明订单接口
package com.hf.mapper; import com.hf.model.Orders; import com.hf.model.OrdersExt; public interface OrderMapper { /** * 通过id查找 * @param id * @return */ public OrdersExt findOrderById(int id); } -
在OrderMapper.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.hf.mapper.OrderMapper"> <select id="findOrderById" resultType="ordersExt" parameterType="int"> SELECT o.*,u.username,u.address FROM orders o ,user u WHERE u.id = o.user_id AND o.id = #{id} </select> </mapper> -
在全局配置文件中加载配置文件
<mapper resource="com/hf/mapper/OrderMapper.xml"></mapper> -
测试
@Test public void test1() { OrderMapper mapper = session.getMapper(OrderMapper.class); OrdersExt ordersExt = mapper.findOrderById(3); System.out.println(ordersExt); }
方法二:在Orders类中实现一个User属性
-
在Orders类中添加一个User属性,并提供get/set方法

-
在OrderMapper.java中声明接口方法
/** * 通过id查找 * @param id * @return */ public Orders findOrderById2(int id); -
在OrderMapper.xml中配置,使用resultMap
<!--如果模型里面有模型,使用resultMap--> <resultMap id="orderResultMap" type="orders"> <!--往Orders的模型匹配数据--> <id column="id" property="id"></id> <result column="note" property="note"></result> <result column="number" property="number"></result> <result column="createtime" property="createtime"></result> <!--往User属性匹配数据--> <association property="user" javaType="user"> <id column="user_id" property="id"></id> <result column="username" property="username"></result> <result column="address" property="address"></result> </association> </resultMap> <select id="findOrderById2" resultMap="orderResultMap" parameterType="int"> SELECT o.*,u.username,u.address FROM orders o ,user u WHERE u.id = o.user_id AND o.id = #{id} </select> -
测试
@Test public void test2() { OrderMapper mapper = session.getMapper(OrderMapper.class); Orders order = mapper.findOrderById2(3); System.out.println(order); }
一对多
需求:
根据订单id查找订单,用户信息以及订单详细信息
一个订单对应多个订单详细
-
定义一个订单详细信息OrderDetail类
package com.hf.model; /** * 订单详情 */ public class OrderDetail { private Integer id;//订单详情id private Integer itemsId;//商品id private Integer itemsNum; //购买数量 public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public Integer getItemsId() { return itemsId; } public void setItemsId(Integer itemsId) { this.itemsId = itemsId; } public Integer getItemsNum() { return itemsNum; } public void setItemsNum(Integer itemsNum) { this.itemsNum = itemsNum; } @Override public String toString() { return "OrderDetail{" + "id=" + id + ", itemsId=" + itemsId + ", itemsNum=" + itemsNum + '}'; } } -
在Orders类中声明一个OrderDetail集合,并提供get/set方法

-
在OrderMapper.java中声明接口方法
/** * 通过id查找 * @param id * @return */ public Orders findOrderById2(int id); -
在OrderMapper.xml中配置
<resultMap id="orderResultMap3" type="orders"> <!--往Orders的模型匹配数据--> <id column="id" property="id"></id> <result column="note" property="note"></result> <result column="number" property="number"></result> <result column="createtime" property="createtime"></result> <!--往User属性匹配数据--> <association property="user" javaType="user"> <id column="user_id" property="id"></id> <result column="username" property="username"></result> <result column="address" property="address"></result> </association> <!--往orders中的orderDetails匹配数据 注意:集合的类型使用ofType而不是javaType --> <collection property="orderDetails" ofType="orderDetail"> <id column="detail_id" property="id"></id> <result column="items_id" property="itemsId"></result> <result column="items_num" property="itemsNum"></result> </collection> </resultMap> <select id="findOrderById3" resultMap="orderResultMap3" parameterType="int"> SELECT o.*, u.username, u.address, od.id detail_id, od.items_id, od.items_num FROM orders o, user u, orderdetail od WHERE o.user_id = u.id AND od.orders_id = o.id AND o.id = #{id} </select> -
测试
@Test public void test3() { OrderMapper mapper = session.getMapper(OrderMapper.class); Orders order = mapper.findOrderById3(3); System.out.println(order); System.out.println(order.getUser()); System.out.println(order.getOrderDetails()); }
多对多
需求:
查询所有用户及订单
思路

-
定义模型
package com.hf.model; import java.io.Serializable; import java.util.Date; import java.util.List; public class User implements Serializable { private int id; private String username;// 用户姓名 private String sex;// 性别 private Date birthday;// 生日 private String address;// 地址 /*用户和订单,一对多关系*/ private List<Orders> orders; public User(String username, String sex, Date birthday, String address) { this.username = username; this.sex = sex; this.birthday = birthday; this.address = address; } public User() { } public int getId() { return id; } public void setId(int id) { this.id = id; } public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public String getSex() { return sex; } public void setSex(String sex) { this.sex = sex; } public Date getBirthday() { return birthday; } public void setBirthday(Date birthday) { this.birthday = birthday; } public String getAddress() { return address; } public void setAddress(String address) { this.address = address; } public List<Orders> getOrders() { return orders; } public void setOrders(List<Orders> orders) { this.orders = orders; } @Override public String toString() { return "User [id=" + id + ", username=" + username + ", sex=" + sex + ", birthday=" + birthday + ", address=" + address + "]"; } }package com.hf.model; import java.util.Date; import java.util.List; public class Orders{ private Integer id; private Integer user_id; private String note; private String number; private Date createtime; private User user; /*一对多数据封装*/ private List<OrderDetail> orderDetails; public List<OrderDetail> getOrderDetails() { return orderDetails; } public void setOrderDetails(List<OrderDetail> orderDetails) { this.orderDetails = orderDetails; } public User getUser() { return user; } public void setUser(User user) { this.user = user; } public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public Integer getUser_id() { return user_id; } public void setUser_id(Integer user_id) { this.user_id = user_id; } public String getNote() { return note; } public void setNote(String note) { this.note = note; } public String getNumber() { return number; } public void setNumber(String number) { this.number = number; } public Date getCreatetime(){ return createtime; } public void setCreatetime(Date createtime) { this.createtime = createtime; } @Override public String toString() { return "Orders{" + "id=" + id + ", user_id=" + user_id + ", note='" + note + '\'' + ", number='" + number + '\'' + ", createtime=" + createtime + '}'; } }package com.hf.model; /** * 订单详情 */ public class OrderDetail { private Integer id;//订单详情id private Integer itemsId;//商品id private Integer itemsNum; //购买数量 private Items items;//商品信息 public Items getItems() { return items; } public void setItems(Items items) { this.items = items; } public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public Integer getItemsId() { return itemsId; } public void setItemsId(Integer itemsId) { this.itemsId = itemsId; } public Integer getItemsNum() { return itemsNum; } public void setItemsNum(Integer itemsNum) { this.itemsNum = itemsNum; } @Override public String toString() { return "OrderDetail{" + "id=" + id + ", itemsId=" + itemsId + ", itemsNum=" + itemsNum + '}'; } }package com.hf.model; public class Items { private Integer id; private String name; private Float price; private String detail; public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public Float getPrice() { return price; } public void setPrice(Float price) { this.price = price; } public String getDetail() { return detail; } @Override public String toString() { return "Items{" + "id=" + id + ", name='" + name + '\'' + ", price=" + price + ", detail='" + detail + '\'' + '}'; } public void setDetail(String detail) { this.detail = detail; } } -
在OrderMapper.java中声明接口方法
/** * 查询所有用户及订单 * @return */ public List<User> findUserAndOrderAll(); -
在OrderMapper.xml中配置
<!--===========多对多 查询用户和订单================--> <resultMap id="userResultMap" type="user"> <!--user的属性--> <id column="id" property="id"/> <result column="username" property="username"/> <result column="address" property="address"/> <!--user里的orders属性--> <collection property="orders" ofType="orders"> <id column="order_id" property="id"/> <result column="number" property="number"/> <result column="createtime" property="createtime"/> <result column="note" property="note"/> <!--嵌套,在orders中为orderDetails赋值--> <collection property="orderDetails" ofType="orderDetail"> <id column="detail_id" property="id"/> <result column="items_id" property="itemsId"/> <result column="items_num" property="itemsNum"/> <!--嵌套,在orderDetail中为items赋值--> <association property="items" javaType="items"> <id column="items_id" property="id"/> <result column="name" property="name"/> <result column="price" property="price"/> <result column="detail" property="detail"/> </association> </collection> </collection> </resultMap> <select id="findUserAndOrderAll" resultMap="userResultMap"> SELECT u.id, u.username, u.address, o.id order_id, o.number, o.createtime, o.note, od.id detail_id, od.items_id, od.items_num, it.name, it.price, it.detail FROM user u, orders o, orderdetail od, items it WHERE o.user_id = u.id AND o.id = od.orders_id AND od.items_id = it.id </select> -
测试
@Test public void test4() { OrderMapper mapper = session.getMapper(OrderMapper.class); List<User> users = mapper.findUserAndOrderAll(); for (User user : users) { System.out.println("用户信息:"+user); System.out.println("---------------------------------"); for (Orders order : user.getOrders()) { System.out.println("订单信息:"+order); for (OrderDetail orderDetail : order.getOrderDetails()) { System.out.println("订单详细信息:"+orderDetail +"---商品信息:"+orderDetail.getItems()); } System.out.println("---------------------------------"); } } }

这篇博客介绍了MyBatis中三种关联查询的实现方式:一对一查询,包括扩展类实现和在Orders类中直接添加User属性的方法;一对多查询,涉及如何获取订单及其详细信息;以及多对多查询,讲解了如何查询用户及他们的多个订单。
4182

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



