MyBatis(五):mapper 获取返回值的方式

mapper 的查询 SQL 语句可能获得多种返回值,本节将说明如何获取这些返回值。

查询单行记录

前面已经演示过,可以通过配置

<!--  User getUserById(Integer id);  -->
<select id="getUserById" resultType="User">
    select * from t_user where id = #{id}
    <!--        select * from t_user where id = '${id}'-->
</select>

查询单行记录。

注意:这里的查询底层使用的是 SqlSession 的 selectOne() 函数,如果查询结果有多条记录,将会抛出 TooManyResultsException 异常

查询多行记录

通过配置

<!--  List<User> getAllUser();  -->
<select id="getAllUser" resultType="User">
    select * from t_user
</select>

可以查询多行记录。

注意:如果查询到一条记录,不会报错

查询单行单列(单一值)

有时候,我们需要获得单一的某个字面值,我们可以通过下面的方式实现结果

<!-- Integer getCount(); -->
<select id="getCount" resultType="java.lang.Integer">
    select count(*) from t_user
</select>

事实上,由于 MyBatis 已经为常用类型设置过「别名」,这里的 java.lang.Integer 不写全类名,写 Integer, int, integer 甚至于 intEGeR 都可以。别名信息可以参考 MyBatis 手册,其基本规律是:Java 基本类型的别名是在其前面加一个下划线;基本类型的封装类以及集合类的别名就是其本身。

查询一条记录为 Map

有时候,我们只希望获得某条记录的部分信息,或者经过多表联查之后,查询到的表的信息根本没有实体类与之对应。这时,我们可以选择将查询结果转换为 Map,其中的键为字段名,值为字段值。

<!--Map<String, Object> getUserByIdToMap(@Param("id") Integer id);-->
<select id="getUserByIdToMap" resultType="map">
    select id, username, password from t_user where id = #{id}
</select>

注意:当某个字段值为 NULL 时,MyBatis 不会将该字段加入 Map。

查询多条记录为 Map

如果结果存在多条记录,而当个 Map 只能储存一条记录信息,如果使用 Map 作为返回值,将会抛出 TooManyResultsException 异常,通过两种方式来将这种记录转换为 Map 集合:

  1. 使用一个包含 Map 的 List 集合来存储这多条记录。

    <!--List<Map<String, Object>> getAllUserToMap();-->
    <select id="getAllUserToMap" resultType="Map">
        select id, username, password from t_user
    </select>
    

    这种方式获得的结果是一个 Map 集合的 List 集合。

  2. 使用某个字段作为 Map 集合的键,整一行记录作为 Map 集合的值(整行记录也是 Map 集合),返回的结果类型应该是 Map<String, Map<String, Object>>。要得到这种形式的结果,需要在函数定义时指定外层 Map 的键 @MapKey(value = "字段名")

    @MapKey("id")
    Map<String, Object> getAllUserToMap();
    
    <select id="getAllUserToMap" resultType="Map">
        select id, username, password from t_user
    </select>
    

    测试结果:

    {1={password=123456, id=1, username=admin}, 7={password=666666, id=7, username=lucy}}
    

小结

  • 通过配置 ResultType 属性可以获得返回值,如果设置的返回值是对象类型,就要求属性配置的返回类的属性和查询得到的记录的属性一一对应,如果设置的返回值是字面值类型,查询结果必须是单行单列的;
  • 查询单行记录和多行记录的 mapper 配置是完全一致的,它们的区别在于 mapper 类的方法返回值不同,如果返回值是单个对象,MyBatis 将调用 selectOne 方法,否则调用 select 方法返回对象集合。需要注意的是,select 兼容 selectOne,但是如果查询到多条记录,selectOne 方法将会报错。
  • MyBatis 支持查询记录为 Map 型,它会将查到的字段作为 Map 的键,字段值作为 Map 的值;
  • 查询多条记录为 Map,有两种方式,一种是设置 mapper 类的方法返回值为 List<Map>,这样 MyBatis 将调用 select 方法而不是 selectOne;另一种是给方法配置 @MapKey("key") 注解,这种配置返回的将会是 Map<key, Map<字段名, 字段值>>,这里需要保证 key 值不重复,一般使用主键。