1. 疑问

在之前的章节中我们阐述了如何用Mybatis实现检查的查询,而我们实际的需求中,绝大部分查询都不只是针对单张数据表的简单查询,所以我们接下来要看一下Mybatis如何实现联合查询。

2. 数据库准备

--销售单表
CREATE TABLE tbSaleM (
ID INT IDENTITY(1,1),
SaleDate DATETIME, --销售日期
ClientName NVARCHAR(200), --客户名称
AmountSum NUMERIC(16,4), --销售数量汇总
MoneySum NUMERIC(16,4), --销售金额汇总
PRIMARY KEY (ID) --主键
)
--销售明细表
CREATE TABLE tbSaleD (
ID INT IDENTITY(1,1),
MID INT, --对应销售单表的ID
PartID INT, --商品ID,在我们之前建立的商品信息表里
SaleAmount NUMERIC(16,4), --销售数量
SalePrice NUMERIC(16,4), --销售单价
SaleMoney NUMERIC(16,4) --销售金额
PRIMARY KEY (MID, PartID) --主键
)

我们建立两个数据表来记录一个完整的销售过程。tbSaleM记录销售日期、客户名称的主要单据信息,tbSaleD用来记录具体销售了哪些商品。其中tbSaleD的MID取值为tbSaleM中的ID,tbSaleD中的Part取值为之前章节中tbInfoPart的ID。

然后我们生成一条用来测试的销售数据:

DECLARE @LastID INT
INSERT INTO tbSaleM (SaleDate, ClientName, AmountSum, MoneySum)
VALUES (GETDATE(), '张三', 3, 4998.800000)
SET @LastID=@@IDENTITY
INSERT INTO tbSaleD (MID, PartID, SaleAmount, SalePrice, SaleMoney)
VALUES (@LastID, 1, 2, 1099.900000, 1099.900000*2)
INSERT INTO tbSaleD (MID, PartID, SaleAmount, SalePrice, SaleMoney)
VALUES (@LastID, 2, 1, 2799.000000, 2799.000000*1)

3. 采购单实体类的建立

1)销售单表(注意这里面有一个的saleDs属性):

package com.mybatis.entity;

import java.util.Date;
import java.util.List; public class SaleM {
private Integer id;
private Date saleDate;
private String clientName;
private Float amountSum;
private Float moneySum;
private List<SaleD> saleDs; public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public Date getSaleDate() {
return saleDate;
}
public void setSaleDate(Date saleDate) {
this.saleDate = saleDate;
}
public String getClientName() {
return clientName;
}
public void setClientName(String clientName) {
this.clientName = clientName;
}
public Float getAmountSum() {
return amountSum;
}
public void setAmountSum(Float amountSum) {
this.amountSum = amountSum;
}
public Float getMoneySum() {
return moneySum;
}
public void setMoneySum(Float moneySum) {
this.moneySum = moneySum;
}
public List<SaleD> getSaleDs() {
return saleDs;
}
public void setSaleDs(List<SaleD> saleDs) {
this.saleDs = saleDs;
}
}

2)销售明细表(注意这里面的partInfo属性)

package com.mybatis.entity;

public class SaleD {
private Integer id;
private Integer mId;
private Integer partId;
private Float saleAmount;
private Float salePrice;
private Float saleMoney;
private PartInfo partInfo; public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public Integer getmId() {
return mId;
}
public void setmId(Integer mId) {
this.mId = mId;
}
public Integer getPartId() {
return partId;
}
public void setPartId(Integer partId) {
this.partId = partId;
}
public Float getSaleAmount() {
return saleAmount;
}
public void setSaleAmount(Float saleAmount) {
this.saleAmount = saleAmount;
}
public Float getSalePrice() {
return salePrice;
}
public void setSalePrice(Float salePrice) {
this.salePrice = salePrice;
}
public Float getSaleMoney() {
return saleMoney;
}
public void setSaleMoney(Float saleMoney) {
this.saleMoney = saleMoney;
}
public PartInfo getPartInfo() {
return partInfo;
}
public void setPartInfo(PartInfo partInfo) {
this.partInfo = partInfo;
}
}

4. 销售单的查询

我们知道,如果是在SQL中查询这个销售单,应该这样查询:

SELECT A.ID AS AID, A.SaleDate, A.ClientName, A.AmountSum, A.MoneySum,
B.ID AS BID, B.MID, B.PartID, B.SaleAmount, B.SalePrice, B.SaleMoney,
C.ID As CID, C.PartCode, C.PartName, C.SalePrice AS CSalePrice, C.Unit
FROM tbSaleM A INNER JOIN tbSaleD B ON A.ID=B.MID
INNER JOIN tbInfoPart C ON B.PartID=C.ID
WHERE A.ID=1

然后我们需要Mybatis将这个查询结果填充到SaleM的实体类中,那么Mybatis中应该怎么配置呢?

1) 首先我们仍然需要在com.mybatis.dao.PartDao中增加一个接口函数:

/**
* 查询销售单
* @param id 要查询的销售单ID
* @return 返回销售单信息
*/
public SaleM getSaleM(int id);

2) 相对应的在PartMapper中需要增加此接口函数的实现,配置如下:

    <!-- 注意这里不是resultType,而是resultMap,其取值SaleM来源为下面resultMap标签中的id属性 -->
<select id="getSaleM" parameterType="int" resultMap="SaleM">
SELECT A.ID AS AID, A.SaleDate, A.ClientName, A.AmountSum, A.MoneySum,
B.ID AS BID, B.MID, B.PartID, B.SaleAmount, B.SalePrice, B.SaleMoney,
C.ID As CID, C.PartCode, C.PartName, C.SalePrice AS CSalePrice, C.Unit
FROM tbSaleM A INNER JOIN tbSaleD B ON A.ID=B.MID
INNER JOIN tbInfoPart C ON B.PartID=C.ID
WHERE A.ID=#{id}
</select> <resultMap type="com.mybatis.entity.SaleM" id="SaleM">
<id property="id" column="AID"/>
<result property="saleDate" column="SaleDate"/>
<result property="clientName" column="ClientName"/>
<result property="amountSum" column="AmountSum"/>
<result property="moneySum" column="MoneySum"/>
<collection property="saleDs" ofType="com.mybatis.entity.SaleD">
<id property="id" column="BID"/>
<result property="mId" column="MID"/>
<result property="partId" column="PartID"/>
<result property="saleAmount" column="SaleAmount"/>
<result property="salePrice" column="SalePrice"/>
<result property="saleMoney" column="SaleMoney"/>
<association property="partInfo" javaType="com.mybatis.entity.PartInfo">
<id property="id" column="CID"/>
<result property="partCode" column="PartCode"/>
<result property="partName" column="PartName"/>
<result property="salePrice" column="CSalePrice"/>
<result property="unit" column="Unit"/>
</association>
</collection>
</resultMap>

3) 测试下查询结果

public static void main(String[] args) {
InputStream iStream = TestMain.class.getClassLoader().getResourceAsStream("mybatis.xml");
SqlSessionFactory sessionFactory = new SqlSessionFactoryBuilder().build(iStream);
SqlSession session = sessionFactory.openSession();
String statement = "com.mybatis.dao.PartDao.getSaleM";
SaleM saleM = session.selectOne(statement, 1);
session.commit();
session.close(); System.out.println("销售"+saleM.getId()+":"+
saleM.getClientName()+" 于 "+
saleM.getSaleDate()+
" 购买了共"+saleM.getAmountSum()+
"件商品,总售价:"+saleM.getMoneySum()+"元");
System.out.println("其中包含:");
for (SaleD saleD : saleM.getSaleDs()) {
System.out.println("----["+
saleD.getPartInfo().getPartName()+"] "+
saleD.getSaleAmount()+
saleD.getPartInfo().getUnit()+",单价"+
saleD.getSalePrice()+",共"+
saleD.getSaleMoney()+"元"); }
}

打印结果为:

销售1:张三 于  Sun Feb  :: CST   购买了共3.0件商品,总售价:.8元
其中包含:
----[TCL D32E161 32英寸 内置wifi 在线影视 窄边LED网络液晶电视] .0台,单价1099.,共2199.8元
----[TCL D50A710 50英寸 40万小时视频 全高清 内置WiFi 八核安卓智能LED液晶电视] .0台,单价2799.,共2799.0元

5. resultMap释义

collection:实现1对多关联, association :实现1对1关联。

result:规定了查询结果列和JavaBean的对应关系,其中property为JavaBean的属性名,column为查询结果列名。

id:功能同result,但是标记为id可以帮助提高整理性能。

6. 目录结构

Mybatis实现联合查询(六)的更多相关文章

  1. MyBatis 示例-联合查询

    简介 MyBatis 提供了两种联合查询的方式,一种是嵌套查询,一种是嵌套结果.先说结论:在项目中不建议使用嵌套查询,会出现性能问题,可以使用嵌套结果. 测试类:com.yjw.demo.JointQ ...

  2. mybatis plus 联合查询

    在xml中只需要需要写如下的代码即可实现分页: <select id="selectUserList" parameterType="map" resul ...

  3. Mybatis的联合查询

    数据库表结构 department employee 要求一 现在的要求是输入 id 把 employee 表的对应员工数据查询出来,并且查询出该员工的所处部门信息 JavaBean public c ...

  4. mybatis的嵌套查询(嵌套查询nested select和嵌套结果nested results查询)区别

    (转自:http://blog.csdn.net/canot/article/details/51485955) Mybatis表现关联关系比hibernate简单,没有分那么细致one-to-man ...

  5. mybatis的嵌套查询与嵌套结果查询的不同

    原文:https://blog.csdn.net/qq_39706071/article/details/85156840 实体类: 嵌套查询mapper方法:嵌套查询的弊端:即嵌套查询的N+1问题尽 ...

  6. Mybatis.net与MVC入门配置及联合查询动态SQL拼接和简单事务

    第一次学习Mybatis.net,在博客园也找到好多资料,但是在配置成功之后也遇到了一些问题,尤其是在动态SQl拼接时候,这里把遇到的问题还有自己写的一个Demo贴出来,希望能帮到新手,有不适合的地方 ...

  7. MyBatis基础入门《六》Like模糊查询

    MyBatis基础入门<六>Like模糊查询 描述: 未改动的文件,不再粘贴出来.项目中SQL的xml映射文件重要标签如下: mapper namespace cache 配置给定命令空间 ...

  8. Mybatis中@select注解联合查询

    前言 在项目中经常会使用到一些简单的联合查询获取对应的数据信息,我们常规都是会根据对应的mapper接口写对应的mapper.xml的来通过对应的业务方法来调用获取,针对这一点本人感觉有点繁琐,就对@ ...

  9. MyBatis 多表联合查询及优化 以及自定义返回结果集

    下面就来说一下 mybatis 是通过什么来实现多表联合查询的.首先看一下表关系,如图: 这 里,我已经搭好了开发的环境,用到的是 SpringMVC + Spring + MyBatis,当然,为了 ...

随机推荐

  1. python基础数据类型--元组(tuple)

    python基础数据类型--元组(tuple) 一.元组的定义和特性 定义:与列表相似,只不过就是将[ ] 改成 ( ) 特性:1.可以存放多个值 2.不可变 3.按照从左到右的顺序定义元组元素,下标 ...

  2. Mac安装软件提示破损

    安装提示破损 zhong终端输入 sudo spctl --master-disable 就可以顺利打开啦

  3. ssh服务启动失败 /var/empty must be owned by root and not group or world-writable.

    输入 /etc/rc.d/init.d/sshd start 启动sshd服务,报如下错误: /var/empty must be owned by root and not group or wor ...

  4. 全选checkbox只能执行一次的问题

    现象:第一次运行,点select all那个checkbox,可以全选,再点一次,也可以全部取消.但是,之后不管怎样点击,都没有用了…… <input type="checkbox&q ...

  5. 小程序跳坑之JSON字符串转换JSON对象

    常见的JSON字符串转换有很多,这里只讲我遇到过的小程序中用到的转换. 通常我们在小程序中用到的地方是,请求一个数据表或者请求一个接口,拿到了一堆数据,里面包含有各种字段数组,头像,图片,详情,地址, ...

  6. 我的Java语言学习日志1_"简单的银行管理系统实现"

    设计步骤:注意:本篇代码,直接建两个类( Bank_Account.BankManage)在BankManage往里面填方法就行.是为了让和我一样自学朋友可以更快的接受.但是代码优化的空间还是很大的( ...

  7. 087-把PHP数组中的元素按随机顺序重新排列shuffle

    <?php $arr=array(3,23,'A','f','123','hello'); //定义一个数组 echo '排序之前的数组信息:<br>'; print_r($arr) ...

  8. 实验吧-杂项-啦啦啦(数据包http导出、图片拼接)

    比较综合的一道题. 1.数据包数据提取 首先下载数据包,一般数据包都是抓取的一些数据,需要对数据进行分析. 用wireshark打开数据包,筛选出http协议的数据,发现有两个是上传的数据: 我们就看 ...

  9. 方便快捷组织页面 DOM 的 js 引模板擎 —— doT.js 的使用

    —————————————————————————————————————————— ——————————————————————————————————————————

  10. 【LeetCode】跳跃游戏II

    [问题]给定一个非负整数数组,你最初位于数组的第一个位置.数组中的每个元素代表你在该位置可以跳跃的最大长度.你的目标是使用最少的跳跃次数到达数组的最后一个位置. 示例: 输入: [,,,,] 输出: ...