MyBatis之resultMap的作用和xml配置折腾

简单的搭建。

MyBatis实战——前身iBatis、基础环境搭建和如何"钓鱼" 这篇写了基础的环境搭建和代码操作。

我这里是使用了xml加interface结合的方法进行操作。现有Employee类。如果是简单的select,可以看看下面简单的例子。

Employee.java

public class Employee {//省略get set 方法
	private int id;
	private String first_name;
	private String last_name;
	private int salary;
}

EmployeeMapper.java

package com.mybatis3.mappers;

import model.Employee;

public interface EmployeeMapper
{
	Employee findEmployeeById(Integer a);
}

EmployeeMapper.xml(和EmployeeMapper.java位于同个package中

<?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.mybatis3.mappers.EmployeeMapper">
  <select id="findEmployeeById" resultType="model.Employee">
    select * from Employee where id = #{abc} <!-- 后面发现这个参数名这里填什么都无所谓,能映射到 -->
  </select>
</mapper>  

mybatis-config.xml的mappers映射改成:

<mapper class="com.mybatis3.mappers.EmployeeMapper" />

进行查询操作。

public class Factory {
    public static void main(String[] args) {
        String configxml = "mybatis-config.xml";
        InputStream is = null;
        try {
            is = Resources.getResourceAsStream(configxml);
        } catch (IOException e) {
            e.printStackTrace();
        }
        SqlSessionFactory sf = new SqlSessionFactoryBuilder().build(is);
        SqlSession s = sf.openSession();
        EmployeeMapper employeeMapper =  s.getMapper(EmployeeMapper.class);
        Employee e =  employeeMapper.findEmployeeById(47);
        System.out.println(e.getFirst_name());
        System.out.println(e.getLast_name());
        System.out.println(e.getSalary());
        s.close();
    }
}  

这是单表查询的时候,那么问题就来了。如果是多表复杂的查询。现在有了一张新表Employer,假如你是框架的设计者,会让Employee的字段全部丢到Employer中吗,显然不合适。

这是MyBatis提供了resultmap的方法。先看看单独一个类也可以使用resultmap进行映射。

Employer类

public class Employer {
	private int id;//省略set get 方法
	private int employee_id;
	private String name;
	private Employee em;
}

EmployerMapper.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.mybatis3.mappers.EmployerMapper">
	<resultMap id="Employer" type="model.Employer">
		<id property="id" column="id" />	<!-- id相当于resultmap的引用的唯一标识-->
		<result property="name" column="name" />  <!-- property对应javabean的属性名,column对应数据库字段名 -->
		<result property="employee_id" column="employee_id" />
	</resultMap>

	<select id="findEmployeeById" resultMap="Employer">
		select * from Employer where id = #{abc}
	</select>
</mapper>

测试:

public class Factory {
    public static void main(String[] args) {
        String configxml = "mybatis-config.xml";
        InputStream is = null;
        try {
            is = Resources.getResourceAsStream(configxml);
        } catch (IOException e) {
            e.printStackTrace();
        }
        SqlSessionFactory sf = new SqlSessionFactoryBuilder().build(is);
        SqlSession s = sf.openSession();
        EmployerMapper employerMapper =  s.getMapper(EmployerMapper.class);
        Employer e2 =  employerMapper.findEmployeeById(1);
        System.out.println(e2.getEmployee_id());
        System.out.println(e2.getName());
        s.close();
    }
}  

折腾resultMap的id,result属性:

接下来开始折腾了。将EmployerMapper.xml里面改成只剩:

	<resultMap id="Employer" type="model.Employer">
	</resultMap>

	<select id="findEmployeeById" resultMap="Employer">
		select * from Employer where id = #{abc}
	</select>

发现还是能正常映射。但是如果改javabean的一个属性:

	private int employeeid;
	public int getEmployeeid() {
		return employeeid;
	}
	public void setEmployeeid(int employee_id) {
		this.employeeid = employee_id;
	}

这样最后取值是取不到的,因为映射不到。那究竟是属性名还是通过getset方法的名字映射呢。再折腾:

	private int employeeid;
	public int getEmployee_id() {
		return employeeid;
	}
	public void setEmployee_id(int employee_id) {
		this.employeeid = employee_id;
	}

employeeid属性名与数据库字段名不对应,但是get,set的方法名是和数据库字段名对应的。运行正常。

如果不想在配置这里瞎折腾,JavaBean字段名保持和数据库字段名是最好的选择。

折腾resultMap extends属性,表关联查询。

Employer.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.mybatis3.mappers.EmployerMapper">
	<resultMap id="Employer" type="model.Employer">
	</resultMap>
	<resultMap type="model.Employer" id="EmployerWithEmployee"
		extends="Employer">
		<result property="em.id" column="id" />
		<result property="em.first_name" column="first_name" />
		<result property="em.last_name" column="last_name" />
		<result property="em.salary" column="salary" />
	</resultMap>
	<select id="findEmployeeById2" resultMap="EmployerWithEmployee">
		select employee_id,name,b.first_name,b.salary,b.last_name from Employer a
		left join Employee b on a.employee_id=b.id where a.id = #{abc}
	</select>
</mapper>

测试:

        SqlSessionFactory sf = new SqlSessionFactoryBuilder().build(is);
        SqlSession s = sf.openSession();
        EmployerMapper employerMapper =  s.getMapper(EmployerMapper.class);
        Employer e2 =  employerMapper.findEmployeeById2(1);
        System.out.println(e2.getEmployee_id());
        System.out.println(e2.getName());
        System.out.println(e2.getEm().getFirst_name());
        System.out.println(e2.getEm().getLast_name());

注意这次的em不再是和上面第一个折腾的一样,是和方法名一致的。这次是和属性名一致。不然会报错。

而且MyBatis的关联查询就这么简单,还是一样的关联语句,只不过加了一些映射配置。

折腾association

extends拓展看起来挺好,但是讲到解耦的话,你extends出来是个不伦不类的东西。本身我就有Employee的存在。

所以,这时association出现了。

<mapper namespace="com.mybatis3.mappers.EmployerMapper">
	<resultMap id="Employee" type="model.Employee">
		<id property="id" column="id" />
		<result property="first_name" column="first_name" />
		<result property="last_name" column="last_name" />
		<result property="salary" column="salary" />
	</resultMap>

	<resultMap id="Employer" type="model.Employer">
		<id property="id" column="id" />	<!-- id相当于resultmap的引用的唯一标识-->
		<result property="name" column="name" />  <!-- property对应javabean的属性名,column对应数据库字段名 -->
		<result property="employee_id" column="employee_id" />
		<association property="em" resultMap="Employee" />
	</resultMap>
	<select id="findEmployeeById2" resultMap="Employer">
		select employee_id,name,b.first_name,b.salary,b.last_name from Employer a
		left join Employee b on a.employee_id=b.id where a.id = #{abc}
	</select>
</mapper>

测试代码不变:

SqlSessionFactory sf = new SqlSessionFactoryBuilder().build(is);
SqlSession s = sf.openSession();
EmployerMapper employerMapper =  s.getMapper(EmployerMapper.class);
Employer e2 =  employerMapper.findEmployeeById2(1);
System.out.println(e2.getEmployee_id());
System.out.println(e2.getName());
System.out.println(e2.getEme().getFirst_name());
System.out.println(e2.getEme().getLast_name());
s.close();  

但是不同于resultmap使用extends,result标签是不可少的,一旦少了,将获取不到其属性值。

经过上面种种折腾之后终于知道作者讲的作用是什么:最后就明白了书上所讲的ResultMap的作用,映射SQL选择声明的结果到JavaBean属性中。通过一对一和一对多associations可以将简单选择声明映射复杂的声明。

时间: 2024-11-07 12:33:45

MyBatis之resultMap的作用和xml配置折腾的相关文章

MyBatis一对多和多对多xml配置

MyBatis一对多和多对多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.ktcx.

MyBatis 之 使用三 (SqlMapConfig.xml 配置)

下面介绍 MyBatis 的核心配置文件 SqlMapConfig.xml 的配置实用: SqlMapConfig.xml 中配置的内容和顺序如下: properties(属性).settings(配置).typeAliases(类型别名).typeHandlers(类型处理器).                         objectFactory(对象工厂).plugins(插件). environments(环境集合属性对象) environment(环境子属性对象) transac

经典ssm集成------xml配置版

1:IDEA创建maven项目 本次创建的是一个web项目: 一路next下去即可. 这样创建出来的项目,结构会缺失,自己手动把java,resources ,test等目录创建出来即可. 2:在pom文件中引入spring,mybatis,spring mvc依赖 pom.xml配置 <?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.or

笔记:MyBatis XML配置详解

MyBatis 的配置文件包含了影响 MyBatis 行为甚深的设置(settings)和属性(properties)信息.文档的顶层结构如下: configuration 配置 properties 属性 settings 设置 typeAliases 类型命名 typeHandlers 类型处理器 objectFactory 对象工厂 plugins 插件 environments 环境 environment 环境变量 transactionManager 事务管理器 dataSource

mybatis使用注解替代xml配置,动态生成Sql

mybatis使用注解替代xml配置时,遇到判断条件是否为null或者为空时,@Select很难搞定,不知道怎么办? mybatis3中增加了使用注解来配置Mapper的新特性,使用 SelectProvider来动态生成sql. 典型的使用场景 1. 无参数@SelectProvide方法在Mapper接口方法上和@SelectProvide指定类方法上,均无参数:UserMapper.java: 1     @SelectProvider(type = SqlProvider.class, 

MyBatis Generator XML 配置参考

<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE generatorConfiguration PUBLIC "-//mybatis.org//DTD MyBatis Generator Configuration 1.0//EN" "http://mybatis.org/dtd/mybatis-generator-config_1_0.dtd"> <

spring,springmvc,mybatis基本整合(一)--xml文件配置方式(2)

spring,springmvc,mybatis基本整合(一)–xml文件配置方式(2)之mapper接口 一,整合结构 二,所需jar包 如上图. 三,整合配置 1,web.xml文件 <?xml version="1.0" encoding="UTF-8"?> <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://j

Java Persistence with MyBatis 3(中文版) 第三章 使用XML配置SQL映射器

关系型数据库和SQL是经受时间考验和验证的数据存储机制.和其他的ORM 框架如Hibernate不同,MyBatis鼓励开发者可以直接使用数据库,而不是将其对开发者隐藏,因为这样可以充分发挥数据库服务器所提供的SQL语句的巨大威力.与此同时,MyBaits消除了书写大量冗余代码的痛苦,它使使用SQL更容易. 在代码里直接嵌套SQL语句是很差的编码实践,并且维护起来困难.MyBaits使用了映射器配置文件或注解来配置SQL语句.在本章中,我们会看到具体怎样使用映射器配置文件来配置映射SQL语句.

mybatis简单sql使用java注解而不是xml配置

一直没有系统的接触mybatis,这就导致对其构建模式并没有清晰的认知,所以项目中所有的查询语句都使用在xml中配置,无论是简单sql,还是复杂sql,无一例外的没有使用java注解,这一点,现在看来,真是后悔莫及!那么请你牢记这点原则吧:mybatis简单sql使用java注解而不是xml配置! 再次使用mybatis,觉得有必要重新认识一下它.这就好比,在你上班的路上,如果偶尔抬抬头扫一扫你的周围,也许就会瞥见不一样的风景──非常有气质的美女映入眼帘,你不得不聚精会神的把眼光的焦点全部集中于