MyBatis一对多双向关联——MyBatis学习笔记之七

简介:

      好久没写MyBatis了,今天继续。

      处理has-one关系需要用到association元素,而处理has many关系则需要用到collection元素。例如本例中,假设一名教师可同时指导多名学生,下面就来介绍如何使用collection元素来实现这种映射,具体的任务是查询出教师及其指导的多个学生的信息(本示例源代码下载页面:http://down.51cto.com/data/490947)。

一、为Teacher实体增加相关属性

      为教师实体增加指导学生集合的属性如下:

1
private  List<Student> supStudents; //指导学生

       并为其增加setter和getter方法,这里略过。

二、TeacherMapper接口

      为实现教师实体映射,应先创建映射器接口如下:

1
2
3
4
5
package  com.abc.mapper;
import  com.abc.domain.Teacher;
public  interface  TeacherMapper {
public  Teacher getById( int  id);
}

三、映射文件

      为教师实体创建的映射文件如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
<? xml  version = "1.0"  encoding = "utf8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<!--与以前一样,namespace的值是对应的映射器接口的完整名称-->
< mapper  namespace = "com.abc.mapper.TeacherMapper" >
<!--TeacherMapper接口中getById方法对应的SQL语句。
查询教师及其指导的学生的信息。由于教师、学生都有
id、name、gender等属性,因此给教师的字段都起了别名-->
< select  id = "getById"  parameterType = "int"  resultMap = "supervisorResultMap" >
select t.id t_id, t.name t_name, t.gender t_gender,
t.research_area t_research_area, t.title t_title,
s.id,s.name, s.gender,s.major,s.grade
from teacher t,student s where t.id=#{id}
and s.supervisor_id = t.id
</ select >
<!--教师实体映射-->
< resultMap  id = "supervisorResultMap"  type = "Teacher" >
< id  property = "id"  column = "t_id" />
< result  property = "name"  column = "t_name" />
< result  property = "gender"  column = "t_gender" />
< result  property = "researchArea"  column = "t_research_area" />
< result  property = "title"  column = "t_title" />
<!--collection元素映射教师的指导学生集合的属性。resultMap
以命名空间名.resultMap的id的形式,引用studentResultMap。
需要注意的是,上面的select语句中学生的字段名/别名应与
studentResultMap中的column属性一致-->
< collection  property = "supStudents"
resultMap = "com.abc.mapper.StudentMapper.studentResultMap" />
</ resultMap >
</ mapper >

       相应地,学生实体的映射文件如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<? xml  version = "1.0"  encoding = "utf8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
< mapper  namespace = "com.abc.mapper.StudentMapper" >
< resultMap  id = "studentResultMap"  type = "Student" >
< id  property = "id"  column = "id" />
< result  property = "name"    column = "name" />
< result  property = "gender"  column = "gender" />
< result  property = "major"   column = "major" />
< result  property = "grade"   column = "grade" />
<!--相应地,在此引用supervisorResultMap,亦采用
命名空间名.resultMap的id的形式。-->
< association  property = "supervisor"
resultMap = "com.abc.mapper.TeacherMapper.supervisorResultMap" />
</ resultMap >
</ mapper >

       在工程的src\resources目录下新建子目录mappers,用来统一存放映射文件。为了能让MyBatis找到这些映射文件,修改其核心配置文件configuration.xml中的mappers元素如下:

1
2
3
4
5
<!--在classpath中以相对路径的形式引用映射文件-->
< mappers >
< mapper  resource = "resources/mappers/StudentMapper.xml" />
< mapper  resource = "resources/mappers/TeacherMapper.xml" />
</ mappers >

       注意:resources目录在工程编译前会被复制到classes目录下(详见工程生成文件build.xml中的copy-resources和compile这两个target),而classes目录会被ant添加到classpath中。

四、执行类

      执行类为CollectionDemo,其内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
package  com.demo;
import  org.springframework.context.ApplicationContext;
import  com.abc.mapper.StudentMapper;
import  com.abc.mapper.TeacherMapper;
import  com.abc.domain.Teacher;
import  com.abc.domain.Student;
import  org.springframework.context.support.ClassPathXmlApplicationContext;
import  java.util.List;
public  class  CollectionDemo
{
private  static  ApplicationContext ctx;
static
{
//在类路径下寻找resources/beans.xml文件
ctx =  new  ClassPathXmlApplicationContext( "resources/beans.xml" );
}
public  static  void  main(String[] args)
{
//从Spring容器中请求映射器
TeacherMapper mapper =
(TeacherMapper)ctx.getBean( "teacherMapper" );
//查询id为1的教师
Teacher teacher = mapper.getById( 1 );
if (teacher ==  null )
{
System.out.println( "未找到相关教师信息。" );
}
else
{
//教师信息
System.out.println( "**********************************************" );
System.out.println( "教师姓名:"  "  "  + teacher.getName());
System.out.println( "教师职称:"  "  "  + teacher.getTitle());
System.out.println( "**********************************************" );
System.out.println( "指导学生信息:" );
//遍历指导的学生
for (Student s : teacher.getSupStudents())
{
System.out.println( "**********************************************" );
System.out.println( s.getName() +  "  "  + s.getGender() +  "  "  + s.getGrade()
"  "  + s.getMajor());
//从学生端访问教师
System.out.println( "指导教师研究方向:"  + s.getSupervisor().getResearchArea());
}
System.out.println( "**********************************************" );
}
}
}

       从中可看出,可以从任意一端访问另一端的对象。

五、修改build.xml

      为了能用ant运行此程序,需修改build.xml中的run target,指定类CollectionDemo为执行类。如下:

1
2
3
4
5
6
7
8
9
< target  name = "run"  depends = "compile" >
<!--指定CollectionDemo为要运行的类-->
< java  fork = "true"  classname = "com.demo.CollectionDemo"
classpathref = "library" >
<!--把classes目录添加到工程的classpath中。
${targetdir}是指引用上面定义的property元素targetdir-->
< classpath  path = "${targetdir}" />
</ java >
</ target >
  运行结果如下:

155714800.png










本文转自 NashMaster2011 51CTO博客,原文链接:http://blog.51cto.com/legend2011/973579,如需转载请自行联系原作者
目录
相关文章
|
9月前
|
SQL Java 数据库连接
MyBatis中一对一、一对多和多对多关联关系的配置详解
MyBatis中一对一、一对多和多对多关联关系的配置详解
281 1
|
9月前
|
SQL Java 数据库连接
33MyBatis - 关联查询(一对多查询)
33MyBatis - 关联查询(一对多查询)
44 0
|
9月前
|
Java 数据库连接 mybatis
【Mybatis用法】Mybatis框架中一对一,一对多association和collection的使用举例方法
【Mybatis用法】Mybatis框架中一对一,一对多association和collection的使用举例方法
63 0
|
2月前
|
SQL 缓存 Java
mybatis 一对多查询
mybatis 一对多查询
49 0
|
19天前
|
Java 数据库连接 mybatis
Mybatis基于注解的一对一和一对多查询
Mybatis基于注解的一对一和一对多查询
23 0
|
19天前
|
SQL Java 数据库连接
Mybatis中一对多mapper配置
Mybatis中一对多mapper配置
18 0
|
2月前
|
Java 数据库连接 mybatis
mybatis的一对多
mybatis的一对多
|
2月前
|
XML SQL Java
mybatis的一对多,多对一,以及多对对的配置和使用
mybatis的一对多,多对一,以及多对对的配置和使用
24 2
|
2月前
|
SQL Java 数据库连接
mybatis关联配置(一对多配置)
mybatis关联配置(一对多配置)
|
2月前
|
存储 XML Java
mybatis使用内部类处理一对多类型数据2
mybatis使用内部类处理一对多类型数据2
23 0