Mybatis集合用法 以及@param参数的原理
Mybatis集合用法 以及@param参数的原理
需求: 批量查询多个数据
难点: 如果使用#{集合}获取的是集合对象的整体.查询无效. 思路: 将数组拆分为单个数据. 可以通过遍历的方式操作 语法: mybatis为了参数取值方便,特意封装了遍历的标签 foreach 关于标签参数说明: <foreach collection=""></foreach> 1.如果传递的参数是数组, 则collection="array" 2.如果传递的参数是list集合, 则collection="list" 3.如果传递的参数是Map集合, 则collection="map中的key" 标签属性说明: 1.collection 集合的名称 2.item 每次遍历的数据的形参变量 3.open 循环的开始标签 4.close 循环的结束标签 5.index 循环遍历下标 一般不用 6.separator 循环遍历的分割符
以数组方式传递
开启测试类:
@Test public void findByIds() { SqlSession sqlSession = sqlSessionFactory.openSession(); DemoUserMapper mapper = sqlSession.getMapper(DemoUserMapper.class); //封装为数组遍历查询 int[] ids = { 12,14,15,23,34,45,56,56}; //封装为list List<Integer> list = new ArrayList<>(); list.add(12); list.add(13); list.add(15); list.add(23); //封装为map HashMap<String, List> map = new HashMap<>(); map.put("myMap", list); List<DemoUser> users = mapper.findByIds(ids); System.out.println("users = " + users); }
sql配置:
<select id="findByIds" resultType="edu.cque.pojo.DemoUser"> select id,name,age,sex from demo_user where id in <foreach collection="array" open="(" close=")" item="id" separator=", "> #{ id} </foreach> </select>
以list方式传递:
@Test public void findByIds() { SqlSession sqlSession = sqlSessionFactory.openSession(); DemoUserMapper mapper = sqlSession.getMapper(DemoUserMapper.class); //封装为数组遍历查询 int[] ids = { 12,14,15,23,34,45,56,56}; //封装为list List<Integer> list = new ArrayList<>(); list.add(12); list.add(13); list.add(15); list.add(23); //封装为map HashMap<String, List> map = new HashMap<>(); map.put("myMap", list); List<DemoUser> users = mapper.findByIds(list); System.out.println("users = " + users); }
接口方法:
List<DemoUser> findByIds(List list);
sql配置:
<select id="findByIds" resultType="edu.cque.pojo.DemoUser"> select id,name,age,sex from demo_user where id in <foreach collection="list" open="(" close=")" item="id" separator=", "> #{ id} </foreach> </select>
运行结果:
以map方式
@Test public void findByIds() { SqlSession sqlSession = sqlSessionFactory.openSession(); DemoUserMapper mapper = sqlSession.getMapper(DemoUserMapper.class); //封装为数组遍历查询 int[] ids = { 12,14,15,23,34,45,56,56}; //封装为list List<Integer> list = new ArrayList<>(); list.add(12); list.add(13); list.add(15); list.add(23); //封装为map HashMap<String, List> map = new HashMap<>(); map.put("myMap", list); List<DemoUser> users = mapper.findByIds(map); System.out.println("users = " + users); }
接口方法:
List<DemoUser> findByIds(Map map);
SQL配置: 注意这里collection中的取值是map中存入的key
<select id="findByIds" resultType="edu.cque.pojo.DemoUser"> select id,name,age,sex from demo_user where id in <foreach collection="myMap" open="(" close=")" item="id" separator=", "> #{ id} </foreach> </select>
我们可以看到,三种不同的方式封装传递的数据,所调用接口方法对应的SQL配置中,只有collection的取值发生了改变.那有没有一种方式让我们的collection取值都是固定不变的呢?
答案是当然有的,当我们在定义接口中的抽象方法的时候,方法里面的参数前面如果加上@param注解,则就可以为当前需要传递的对象进行一层封装,封装为map集合的方式,key为@param的参数,value为@param参数后面的引用变量,在sql配置标签中,则通过这里的key来拿到数据. 下面我们来实战一下
用@param封装的list
@Test public void findByIds() { SqlSession sqlSession = sqlSessionFactory.openSession(); DemoUserMapper mapper = sqlSession.getMapper(DemoUserMapper.class); //封装为数组遍历查询 int[] ids = { 12,14,15,23,34,45,56,56}; //封装为list List<Integer> list = new ArrayList<>(); list.add(12); list.add(13); list.add(15); list.add(23); //封装为map HashMap<String, List> map = new HashMap<>(); map.put("myMap", list); List<DemoUser> users = mapper.findByIds(list); System.out.println("users = " + users); }
接口方法: 这里我们给list进行了封装,后面取数据的时候用的就是myList了
List<DemoUser> findByIds(@Param("myList") List list);
sql配置:
select id,name,age,sex from demo_user where id in <foreach collection="myList" open="(" close=")" item="id" separator=", "> #{id} </foreach> </select>
运行结果:
看到这里,有人可能已经想到了,数组方式和list方式传递数据,和以map方式传递数据好像非常的类似,其实就是在数组或list方式的基础之上用@param进行封装的话,其效果和直接用map形式原理是一样的. 那又有人会想到,如果我们再在map基础之前再封装一层@param注解会是怎样的结果,又应该如何取数据使用呢?
用@param方式封装的map
@Test public void findByIds() { SqlSession sqlSession = sqlSessionFactory.openSession(); DemoUserMapper mapper = sqlSession.getMapper(DemoUserMapper.class); //封装为数组遍历查询 int[] ids = { 12,14,15,23,34,45,56,56}; //封装为list List<Integer> list = new ArrayList<>(); list.add(12); list.add(13); list.add(15); list.add(23); //封装为map HashMap<String, List> map = new HashMap<>(); map.put("myMap", list); List<DemoUser> users = mapper.findByIds(map); System.out.println("users = " + users); }
接口方法:
List<DemoUser> findByIds(@Param("myselfMap") Map map);
sql配置: 可以看到,现在使用collection取数据的话,没有之前那么好拿了,因为map被@param封装之后,就会变成<“myselfMap”,<“myMap”,list>>这种形式,取数据的话,可以先拿外层再拿里层.
至于这么做可能会感觉多此一举,好好的map封装了不是更加的麻烦了吗? 我之所以这么做,只是想让大家更清楚的知道@param是如何对数据进行封装的,掌握真正的核心原理.
<select id="findByIds" resultType="edu.cque.pojo.DemoUser"> select id,name,age,sex from demo_user where id in <foreach collection="myselfMap.myMap" open="(" close=")" item="id" separator=", "> #{ id} </foreach> </select>
运行结果:
上一篇:
多线程四大经典案例
下一篇:
Linux Shell 作业控制命令