欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

MyBatis3系列__05查询补充&resultMap与resultType区别

程序员文章站 2022-04-28 21:51:03
1.查询补充 当你查询一条记录并且是简单查询时,情况相对简单,可以参考以下的例子: 对应的xml文件中: 当查询多条记录时,可以参考以下方式:、 xml中: 2.resultType&resultMap 如果是简单查询,推荐使用resultType(resultMap也能使用,但是比较麻烦),使用方 ......

1.查询补充

当你查询一条记录并且是简单查询时,情况相对简单,可以参考以下的例子:
public employee getempbyid(integer id);
对应的xml文件中:

  <select id="getempbyid" resulttype="com.mybatis.learn.bean.employee">
    select id, last_name lastname, gender, email from tbl_employee where id = #{id}
  </select>

当查询多条记录时,可以参考以下方式:、

 public list<employee> getlistbygender(string gender);

    public map<string, object> getmapbyid(integer id);
   //该注解时指定封存记录的map的key
    @mapkey("lastname")
    public map<string, employee> getmap(string gender);

xml中:

 <!-- 查询多条记录时,若是用list封装结果,resulttype填写list中的每条记录的泛型的全类名 -->
    <select id="getlistbygender" resulttype="com.mybatis.learn.bean.employee">
        select * from tbl_employee where gender=#{gender}
    </select>

    <!-- map存储查询结果时,单条记录可以直接在resulttype中写map -->
    <select id="getmapbyid" resulttype="map">
        select * from tbl_employee where id=#{id}
    </select>

    <!-- map存错多条查询结果时,reuslttype指定的也是里面每条记录的泛型的全类名 -->
    <select id="getmap" resulttype="com.mybatis.learn.bean.employee">
        select * from tbl_employee where gender=#{gender}
    </select>

2.resulttype&resultmap

如果是简单查询,推荐使用resulttype(resultmap也能使用,但是比较麻烦),使用方式在前面演示过了。
resultmap除了可以使用在简单查询情况下,也能使用在resulttype不能胜任的地方,如:联合查询,关联查询等,举个例子:
查询员工信息时包含部门信息:
新建javabean:
package com.mybatis.learn.bean;

import lombok.*;

@getter
@setter
@noargsconstructor
@allargsconstructor
@tostring
public class department {
    private integer deptid;
    private string deptname;
}
在原来的employee类添加新的属性department以及getter setter

private department deparment;
建表sql:

create table `tbl_dept` (
  `dept_id` int(11) unsigned not null,
  `dept_name` varchar(255) default null,
  primary key (`dept_id`)
) engine=innodb default charset=utf8;

修改表tbl_employee ,新增字段dept_id;
此时,由于全部字段存在于两个表中,需要关联查询,已经创建的javabean没有一个能满足要
求,这时可以结合resultmap创建一个:
还是在employeemapper.xml文件中:

    <!--
场景一:
    查询employee的同时查询员工对应的部门
    employee===department
    一个员工有与之对应的部门信息;
    id  last_name  gender  dept_id  dept_name (private department dept;)
 -->
    <!--
        联合查询:级联属性封装结果集
        resultmap:
           id标签:指定主键;
           result标签:指定普通列
               column:指定数据库中的列名
               property:指定对应的javabean中的属性名
               其实,指定id后再指定和数据库不一样的字段即可,不过推荐全部指定
      -->
    <!-- 方式一:关联查询-->
     <resultmap id="myemp" type="com.mybatis.learn.bean.employee">
         <id column="id" property="id"/>
         <result column="last_name" property="lastname"/>
         <result column="gender" property="gender"/>
         <result column="email" property="email"/>
         <result column="dept_id" property="dept.deptid"/>
         <result column="dept_name" property="dept.deptname"/>
     </resultmap>

    <!-- 方式二:使用association定义关联的单个对象的封装规则;-->
     <resultmap id="myemp2" type="com.mybatis.learn.bean.employee">
         <id column="id" property="id"/>
         <result column="last_name" property="lastname"/>
         <result column="gender" property="gender"/>
         <result column="email" property="email"/>
         <!--
            association可以指定联合的javabean对象
            property="dept":指定哪个属性是联合的对象
            javatype:指定这个属性对象的类型[不能省略]
          -->
         <association property="dept" javatype="com.mybatis.learn.bean.department">
             <id column="dept_id" property="deptid"/>
             <result column="dept_name" property="deptname"/>
         </association>

     </resultmap>

    <select id="getfullempbyid" resultmap="myemp">
        select e.id, e.last_name, e.gender, e.email, d.dept_id, d.dept_name
          from tbl_employee e left join tbl_dept d on e.dept_id = d.dept_id
          where id = #{id}
    </select>

    <select id="getfullemp2byid" resultmap="myemp2">
        select e.id, e.last_name, e.gender, e.email, d.dept_id, d.dept_name
          from tbl_employee e left join tbl_dept d on e.dept_id = d.dept_id
          where id = #{id}
    </select>
更改查询mapper:
public employee getfullemp2byid(integer id);
 public employee getfullempbyid(integer id);
这时可以分别测试一下了。
当然,resultmap的意义还不止于此,比如你想分布查询时:
首先开启延迟加载:更改mybatis-config.xml文件:
<!--
            设置延迟加载
            显示的指定每个我们需要更改的配置的值,即使他是默认的。
            防止版本更新带来的问题  
        -->
        <setting name="lazyloadingenabled" value="true"/>
        <setting name="aggressivelazyloading" value="false"/>
原理就是在一个查询中嵌套一个查询,并且在需要关联的字段时才去执行嵌套的查询:
//employeemapper中新增的方法
 public employee getempbystep(integer id);

//employeemapper.xml中新增的内容:
<resultmap id="myempbystep" type="com.mybatis.learn.bean.employee">
        <id column="id" property="id"/>
        <result column="last_name" property="lastname"/>
        <result column="gender" property="gender"/>
        <result column="email" property="email"/>
        <association column="dept_id" property="dept"
                     select="com.mybatis.learn.dao.departmentmapper.getdeptbyid"/>
    </resultmap>

<select id="getempbystep" resultmap="myempbystep">
        select * from tbl_employee where id=#{id}
    </select>

//你也发现了问题对不对,没有对应的嵌套的sql,ok,现在补齐:
//新增departmentmapper:
import com.mybatis.learn.bean.department;

public interface departmentmapper {
    public department getdeptbyid(integer deptid);
}

//以及对应的xml:
 <select id="getdeptbyid" resulttype="com.mybatis.learn.bean.department">
        select * from tbl_dept where dept_id=#{deptid}
    </select>

ok,如何证明分布查询呢:
下面的例子将会证明:

@test
    public void testgetempbystep() {
        string resources = "mybatis-config.xml";
        inputstream inputstream = null;
        try {
            inputstream = resources.getresourceasstream(resources);
        } catch (ioexception e) {
            e.printstacktrace();
        }
        sqlsessionfactory sessionfactory = new sqlsessionfactorybuilder().build(inputstream);
        sqlsession session = sessionfactory.opensession(true);
        employeemapper mapper = session.getmapper(employeemapper.class);
        employee emp = mapper.getempbystep(1);
        system.out.println(emp.getemail());
        system.out.println(emp.getdept());
    }

执行结果如下:
第一次查询,不需要查询dept
debug 03-23 15:51:26,066 ==> preparing: select * from tbl_employee where id=? (basejdbclogger.java:159)
debug 03-23 15:51:26,134 ==> parameters: 1(integer) (basejdbclogger.java:159)
debug 03-23 15:51:26,231 <== total: 1 (basejdbclogger.java:159)
第一次的查询结果,打印了email
eeee
需要dept时,执行对应的sql
debug 03-23 15:51:26,232 ==> preparing: select * from tbl_dept where dept_id=? (basejdbclogger.java:159)
debug 03-23 15:51:26,233 ==> parameters: 1(long) (basejdbclogger.java:159)
debug 03-23 15:51:26,236 <== total: 1 (basejdbclogger.java:159)
department(deptid=1, deptname=组织部)