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. P 1035 插入与归并

    转跳点 :

  2. decodeURIComponent 测试

    var test1="http://www.wljcz.com/My first/"; var nn=encodeURI(test1); var now=decodeURI(tes ...

  3. FULLTEXT INDEX全文索引

    给现有的wxinfo表的sourceUrl 字段创建全文索引 ALTER TABLE wxinfo ADD FULLTEXT INDEX sourceUrl (sourceUrl) 创建全文索引前: ...

  4. mitmproxy(TLS错误)

    一.原来的基础上添加代码 """ This inline script allows conditional TLS Interception based on a us ...

  5. 【踩坑记录】记录一次使用Python logging库多进程打印日志的填坑过程

    背景: 项目使用Python自带的logging库来打印日志 项目部署在一台Centos7的机器上 项目采用gunicorn多进程部署 过程: 1.LOG日志代码封装: 采用logging库,并设置w ...

  6. 十八、SAP中使用IF/ELSE判断语句,以及sy-subrc的用法

    一.sy_subrc为上一条语句的执行结果,如果为0,则表示执行成功. 需要注意的是,IF ELSE语句,每一个关键字都需要带句号 二.执行效果如下 相关代码如下 *&------------ ...

  7. ACM-Satellite Photographs

    题目描述:Satellite Photographs Farmer John purchased satellite photos of W x H pixels of his farm (1 < ...

  8. 苏州大学ICPC集训队新生赛第二场

    A - Score UVA - 1585 水 #include<bits/stdc++.h> using namespace std; int main(){ int n; cin> ...

  9. HDU - 1200 To and Fro

    题意:给定一个,其实是由一个图按蛇形输出而成的字符串,要求按从左到右,从上到下的顺序输出这个图. 分析: 1.把字符串转化成图 2.按要求输出图= = #include<cstdio> # ...

  10. MySQL8.0安装caching_sha2_password问题

    MySQL安装之后无法用工具连接上本地数据库 详情原因可见: https://mysqlserverteam.com/mysql-8-0-4-new-default-authentication-pl ...