在实际开发中,我们常常遇到关联数据的情况,如User对象拥有若干Book对象

每个Book对象描述了归属于一个User信息,这种情况下,我们应该如何处理?

通过单独的Statement操作固然可以实现(通过Statement用于读取用户数据,再手工调用另外一个Statement

根据用户ID返回对应的book信息).不过这样未免失之繁琐.下面我们就看看在ibatis中,如何对关联数据进行操。

ibatis中,提供了Statement嵌套支持,通过Statement嵌套,我们即可实现关联数据的操作。

如下步骤演示一对多关联

1、创建user(id,name,age)表和book(id,name,uid)表

2、POJO类

public class User implements Serializable {

	private static final long serialVersionUID = 1L;
private int id;
private String name;
private int age;
/**
* ibatis一对多关联
*/
private Set<Book> books = new HashSet<Book>();
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
} public Set<Book> getBooks() {
return books;
}
public void setBooks(Set<Book> books) {
this.books = books;
}
}
public class Book {
private int id;
private String name; public int getId() {
return id;
} public void setId(int id) {
this.id = id;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
}
}

3、创建User.xml文件

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE sqlMap
PUBLIC "-//iBATIS.com//DTD SQL Map 2.0//EN"
"http://www.ibatis.com/dtd/sql-map-2.dtd">
<sqlMap namespace="User">
<typeAlias alias="user" type="com.itmyhome.User" />
<typeAlias alias="book" type="com.itmyhome.Book"/> <!-- 一对多查询,一个User对应多个Book -->
<resultMap id="get_user_result" class="user">
<result property="id" column="id"/>
<result property="name" column="name"/>
<result property="age" column="age"/>
<result property="books" column="id" select="User.getBookByUserId"/>
</resultMap> <!-- 查询主表 -->
<select id="getUser" parameterClass="java.lang.String" resultMap="get_user_result">
<![CDATA[
select * from user where id = #id#
]]>
</select> <!-- 查询子表 -->
<select id="getBookByUserId" parameterClass="int" resultClass="book">
<![CDATA[
select *
from book
where uid = #uid#
]]>
</select> </sqlMap>

4、SqlMapConfig.xml

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE sqlMapConfig
PUBLIC "-//iBATIS.com//DTD SQL Map Config 2.0//EN"
"http://www.ibatis.com/dtd/sql-map-config-2.dtd">
<sqlMapConfig>
<settings
cacheModelsEnabled="true"
enhancementEnabled="true"
lazyLoadingEnabled="true"
errorTracingEnabled="true"
maxRequests="32"
maxSessions="10"
maxTransactions="5"
useStatementNamespaces="true" />
<transactionManager type="JDBC">
<dataSource type="SIMPLE">
<property name="JDBC.Driver" value="com.mysql.jdbc.Driver" />
<property name="JDBC.ConnectionURL" value="jdbc:mysql://localhost:3306/ibatis" />
<property name="JDBC.Username" value="root" />
<property name="JDBC.Password" value="root" />
<property name="Pool.MaximumActiveConnections" value="10" />
<property name="Pool.MaximumIdleConnections" value="5" />
<property name="Pool.MaximumCheckoutTime" value="120000" />
<property name="Pool.TimeToWait" value="500" />
<property name="Pool.PingQuery" value="select 1 from ACCOUNT" />
<property name="Pool.PingEnabled" value="false" />
<property name="Pool.PingConnectionsOlderThan" value="1" />
<property name="Pool.PingConnectionsNotUsedFor" value="1" />
</dataSource>
</transactionManager>
<sqlMap resource="com/itmyhome/User.xml" />
</sqlMapConfig>

以上可能需要修改ConnectionURL,Username,Password

5、MyAppSqlConfig.java

import java.io.Reader;
import com.ibatis.common.resources.Resources;
import com.ibatis.sqlmap.client.SqlMapClient;
import com.ibatis.sqlmap.client.SqlMapClientBuilder; public class MyAppSqlConfig {
private static final SqlMapClient sqlMap;
static {
try {
String resource = "SqlMapConfig.xml";
Reader reader = Resources.getResourceAsReader(resource); //读取配置文件
sqlMap = SqlMapClientBuilder.buildSqlMapClient(reader);
} catch (Exception e) {
e.printStackTrace();
throw new RuntimeException("Error initializing MyAppSqlConfig class. Cause: " + e);
}
}
public static SqlMapClient getSqlMapInstance() {
return sqlMap;
}
}


6、测试类

public class UserTest {
public static void main(String[] args) {
SqlMapClient sqlMap = MyAppSqlConfig.getSqlMapInstance();
try {
/**
* 查询ID为5的用户,以下查询假设有数据存在
*/
List list = sqlMap.queryForList("User.getUser","5");
for(int i=0;i<list.size();i++){
User user = (User)list.get(i);
/**
* 得到User所拥有的Book
*/
Set<Book> books = (Set<Book>)user.getBooks();
Iterator ite = books.iterator();
while(ite.hasNext()){
Book book = (Book)ite.next();
System.out.println("用户:"+user.getName()+",书籍: "+book.getName());
}
}
} catch (SQLException e) {
e.printStackTrace();
}
}
}

这里通过在resultMap中定义嵌套查询getBookByUserId,我们实现了关联数据的读取。


项目结构图:

项目源码下载:http://download.csdn.net/detail/itmyhome/7495501

ibatis实战之一对多关联的更多相关文章

  1. ibatis实战之插入数据(自动生成主键)

    ibatis实战之插入数据(自动生成主键) --------- 如果你将数据库设计为使用自动生成的主键,就可以使用ibatis的<selectKey>元素(该元素是<insert&g ...

  2. ibatis实战之中的一个对多关联

    在实际开发中,我们经常遇到关联数据的情况,如User对象拥有若干Book对象 每一个Book对象描写叙述了归属于一个User信息,这样的情况下,我们应该怎样处理? 通过单独的Statement操作固然 ...

  3. MyBatis初级实战之五:一对一关联查询

    欢迎访问我的GitHub https://github.com/zq2599/blog_demos 内容:所有原创文章分类汇总及配套源码,涉及Java.Docker.Kubernetes.DevOPS ...

  4. ibatis实战之OR映射

    相对Hibernate等ORM实现而言,ibatis的映射配置更为简洁直接,以下是一个典型的配置文件. <?xml version="1.0" encoding=" ...

  5. ibatis实战之基础环境搭建

    关于ibatis的介绍.优缺点,以及ibatis和hibernate的比较再此不在赘述,可参阅其他资料. 一.准备工作 1.下载ibatis软件包http://download.csdn.net/de ...

  6. Jmeter+Badboy实战经验三 Jmeter关联相关知识

    1. 什么时候需要使用关联? 有些参数是动态变化的,获取之后,再次操作的时候,参数的值已经发生了变化,这种情况下就会出现脚本不可运行的问题,就需要用到了关联 2. 关联是什么概念? 3.jmeter ...

  7. mysql实战优化之八:关联查询优化

    1. 多表连接类型 1. 笛卡尔积(交叉连接) 在MySQL中可以为CROSS JOIN或者省略CROSS即JOIN,或者使用','  如: 由于其返回的结果为被连接的两个数据表的乘积,因此当有WHE ...

  8. MyBatis初级实战之六:一对多关联查询

    欢迎访问我的GitHub https://github.com/zq2599/blog_demos 内容:所有原创文章分类汇总及配套源码,涉及Java.Docker.Kubernetes.DevOPS ...

  9. Ibatis教程

    Ibatis教程 |字号     转自:http://blog.csdn.net/lhminjava/article/details/1871136 ibatis 开发指南ibatis Quick S ...

随机推荐

  1. SSAS系列——【01】准备知识

    原文:SSAS系列--[01]准备知识 关于SQL Server 产品,我从2004年就开始使用了,SQL Server 2K,2K5,2K8,到如今已经准6年了,说来惭愧,这六年来所涉及的内容都是在 ...

  2. Oracle利用存储过程性 实现分页

    分页的简单配置 在上一次已经说过了 这边说说怎么在存储过程中实现分页 首先建立存储过程 參考 http://www.cnblogs.com/gisdream/archive/2011/11/16/22 ...

  3. C语言库函数大全及应用实例十

    原文:C语言库函数大全及应用实例十                                             [编程资料]C语言库函数大全及应用实例十 函数名: qsort 功 能: 使 ...

  4. Chrome控制台 JS调试

    Chrome控制台 JS调试的一些小技巧 $ $_命令返回最近一次表达式执行的结果,功能跟按向上的方向键再回车是一样的,但它可以做为一个变量使用在你接下来的表达式中. $0~$4则代表了最近5个你选择 ...

  5. 【剑指offer】员工年龄排序

    典型的以空间换时间问题,思路非常重要! /* 员工年龄排序 员工可能有几万名,要求时间复杂度为O(n) 思路:员工的年龄必定在一个范围内,比方0-99,那么我们建立一个大小为100的辅助数组,然后遍历 ...

  6. HDU 4812 D Tree 树分区+逆+hash新位置

    意甲冠军: 特定n点树 K 以下n号码是正确的点 以下n-1行给出了树的侧. 问: 所以,如果有在正确的道路点图的路径 % mod  = K 如果输出路径的两端存在. 多条路径则输出字典序最小的一条. ...

  7. Mysql高级之事务

    原文:Mysql高级之事务 通俗的说事务: 指一组操作,要么都成功执行,要么都不执行.---->原子性 在所有的操作没有执行完毕之前,其他会话不能够看到中间改变的过程-->隔离性 事务发生 ...

  8. linux sendmail 邮件服务器架设(fedora 8)

    linux sendmail 邮件服务器架设(fedora 8) 2009-01-22 17:27 3316人阅读 评论(2) 收藏 举报 邮件服务器linuxprotocolscaching测试lo ...

  9. ASP.NET MVC + EF 利用存储过程读取大数据

    ASP.NET MVC + EF 利用存储过程读取大数据,1亿数据测试很OK 看到本文的标题,相信你会忍不住进来看看! 没错,本文要讲的就是这个重量级的东西,这个不仅仅支持单表查询,更能支持连接查询, ...

  10. PHP中判断输入验证码是否一致

    首先用session将随机生成的验证码的值传到页面,然后获取当前文本框中输入的值  进行对比:代码如下: 生成的随机数,把它传到session里面 <? session_start();   必 ...