Bootstrap

Mybatis 查询结果返回 Map、List<Map>、Pair

Mybatis 查询结果返回 Map、List、Pair

默认:单个、列表

默认单个对象对应一个Map实体
多条数据自动装进一个List

com.jerry.mapper.TestMapper.java

package com.jerry.mapper;

import java.util.List;
import java.util.Map;

public interface TestMapper {
	/**
	 * 查询单个结果直接返回 Map<String, Object>
	 * @param id
	 * @return
	 */
	Map<String, Object> selectById(Long id);
	
	/**
	 * 查询结果列表返回 List<Map<String, Object>>
	 * @param paramsMap
	 * @return
	 */
	List<Map<String, Object>> selectList(Map<String, Object> paramsMap);
}

com.jerry.mapper.TestMapper.xml

map直接设置resultType即可。要list返回多个对象自动就是list,只要设置list里的对象类型即可。

<select id="selectById" resultType="map" parameterType="java.lang.Long">
	select * 
	from test_table as tt
	where tt.id = #{id}
</select>

<select id="selectList" resultType="map" parameterType="map">
	select * 
	from test_table as tt
	<trim prefix="WHERE" prefixOverrides="AND |OR ">
		<!-- 关键字查询 -->
		<if test="keyWords != null and keyWords != ''">
			AND (
				   IFNULL(tt.title, "") like "%"#{keyWords}"%"
				or IFNULL(tt.keys, "") like "%"#{keyWords}"%"
			 )
		</if>
		<if test="searchType != null and searchType != ''">
			AND tt.searchType = #{searchType}
		</if>
	</trim>
</select>

com.jerry.service.impl.TestService.java

package com.jerry.service.impl;

import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.annotation.Resource;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

@Service
@Transactional(readOnly = true)
public class TestService implements ITestService {
	
	@Resource
	private TestMapper testMapper;

	@Override
	public Map<String, Object> allSearch(String keyWords, Integer searchType) {
		Map<String, Object> paramsMap = new HashMap<>();
		paramsMap.put("keyWords", keyWords);
		paramsMap.put("searchType", searchType);
		List<Map<String, Object>> list = testMapper.selectList(paramsMap);
		return list.get(0);
	}

}

返回 Map 集合

查询收藏按 article_id 分组统计。返回类型HashMap。如果默认类型不符合需求,可以添加 一个resultMap来定义一下。

    <!-- 按文章主键 article_id 分组统计收藏量 -->
    <resultMap id="myMap" type="Map" >
        <result property="id" javaType="Long" column="id"/>
        <result property="collection" javaType="Integer" column="collection"/>
    </resultMap>
    <select id="selectCollection" resultMap="myMap">
        SELECT c.article_id AS id, Count(c.id) AS collection
        FROM collections AS c
        GROUP BY c.article_id
    </select>

在接口上添加 @MapKey("id")指定key,通常就是用主键。返回实现Map集合。

 /**
  * 按文章主键 article_id 分组统计收藏量
  */
 @MapKey("id")
 Map<Long, Map<Long, Integer>> selectCollection();

注意:

  • 返回Map时也可以自定义resultMap控制一下类型。

    <resultMap type="HashMap" id="myHashMap">
        <result property="id" javaType="Long" column="id"/>
        <result property="collection" javaType="Long" column="collection"/>
    </resultMap>
    

返回 LinkedHashMap 集合

想返回一个保留结果集顺序的Map,始终没实现。网上说的resultType="java.util.LinkedHashMap"没用。
一直报 HashMap 无法转成 LinkedHashMap 也不知道是哪一步没搞对。
目前只能先返回一个 List<Map<Long, Integer>> 然后再java里转Map了。

返回 Pair

虽然这里接收是用的Pair<Long, Integer>,但mybatis返回实际还是Pair<Integer, Long>,因为id字段在表中int,而统计结果collection默认Long
这会导致一个问题,后续我想再对 pair.getKey()转换类型时,它会理外不是人。

List<Pair<Long, Integer>> selectCollection(); // 后续类型转换时会报错


   <select id="selectCollection" resultType="javafx.util.Pair">
        SELECT c.article_id AS id, Count(c.id) AS collection
        FROM collections AS c
        GROUP BY c.article_id
    </select>

所以正确的应该是使用与Mybatis返回类型一至的变量来接收。这样后续类型转换时才不会报错。

List<Pair<Integer, Long>> selectCollection(); // 正常
;