12.动态SQL
动态SQL是指根据不同的条件,生成不同的SQL语句。
12.1随机生成id
public class IDutils {
public static String getId(){
return UUID.randomUUID().toString().replaceAll("-","");
}
}
//测试
@Test
public void test1(){
System.out.println(IDutils.getId());
}
12.2开启驼峰命名映射
在mybatis-config.xml中
<!--开启字段名和驼峰命名转换,可以将数据表的create_time转换为createTime-->
<setting name="mapUnderscoreToCamelCase" value="true"/>
12.3插入Blog数据
1。接口
//插入数据
int addBlog(Blog blog);
2.BlogMapper.xml
<insert id="addBlog" parameterType="blog">
INSERT INTO blog(id,title,auther,create_time,views) VALUES(#{id},#{title},#{auther},#{createTime},#{views});
</insert>
- parameterType是接口里面的参数,如int addBlog(Blog blog);只能**是blog,**其他类似
3.测试
@Test
public void test1(){
SqlSession sqlSession = MybatisUtils.getSqlSession();
BlogMapper mapper = sqlSession.getMapper(BlogMapper.class);
Blog blog= new Blog();
blog.setId(IDutils.getId());
blog.setTitle("Mybatis好简单");
blog.setAuther("baba");
blog.setCreateTime(new Date());//当前时间
blog.setViews(9999);
mapper.addBlog(blog);
blog.setId(IDutils.getId());
blog.setTitle("Spring好简单");
blog.setViews(999);
mapper.addBlog(blog);
blog.setId(IDutils.getId());
blog.setTitle("SpringMVC好简单");
blog.setViews(9999);
mapper.addBlog(blog);
sqlSession.close();
}
12.4if条件SQL
1.接口
//if查询博客
List<Blog> queryBlogIf(Map map);
2.BlogMapper.xml
这里用了like模糊查询
<select id="queryBlogIf" parameterType="map" resultType="Blog">
select * from blog where 1=1
<if test="title!=null">
and title like "%" #{title} "%"
</if>
<if test="auther!=null">
and auther =#{auther}
</if>
</select>
- List queryBlogIf(Map map);这里范型是Blog,所以resultType也就是Blog
3.测试
@Test
public void TestQueryBlogIf(){
SqlSession sqlSession = MybatisUtils.getSqlSession();
BlogMapper mapper = sqlSession.getMapper(BlogMapper.class);
HashMap map = new HashMap();
map.put("title","Spring");
mapper.queryBlogIf(map);
sqlSession.close();
}
12.5where条件
<select id="queryBlogChoose" parameterType="map" resultType="Blog">
select * from blog
<where>
<if test="title!=null">
title=#{title}
</if>
<if test="auther!=null">
and auther=#{auther}
</if>
</where>
</select>
有了where之后,在select * from blog 不用在加where就可以用多条语句并列查询了,当前一条if不符合条件时,会自动去掉下一条的and或者or。依次类推。
前一条符合,后面会自动加and,在形成一个完成SQL;例如
select * from blog title=#{title} and auther=#{auther}
当后面条件都不满足,就会自动去掉where中间的语句,例如,不传值的时候,就只执行select * from blog
12.6choose—-when条件
<select id="queryBlogChoose" parameterType="map" resultType="Blog">
select * from blog
<where>
<choose>
<when test="title!=null">
title=#{title}
</when>
<when test="auther!=null">
and auther=#{auther}
</when>
<otherwise>
and views =#{views}
</otherwise>
</choose>
</where>
</select>
choose条件,是必须都一个出口,类似java的switch。如果前两个条件都为空,则进入otherwise。所以必须给一个参数给它。通过参数来控制查询动态。where会自动去掉多余的and
注意,后面语句必须加and连接词
12.7update—set
<update id="updateBlog" parameterType="map">
update blog
<set>
<if test="title!=null">
title=#{title},
</if>
<if test="auther!=null">
auther=#{auther}
</if>
</set>
where id=#{id}
</update>
set只能用于update中,可以去掉多余的逗号。功能和where类似,
12.8trim自定义元素
<trim prefix="SET" suffixOverrides=",">
...
</trim>
这个自定义就相当于set元素,去掉多余的逗号
https://mybatis.org/mybatis-3/zh/dynamic-sql.html
12.9Sql片段–提高复用
我们可以将一些相同的代码抽取出来用标签来复用。
<sql id="title-and-auther">
<if test="title!=null">
and title like "%" #{title} "%"
</if>
<if test="auther!=null">
and auther =#{auther}
</if>
</sql>
在我们使用使,用标签来引用
<select id="queryBlogIf" parameterType="map" resultType="Blog">
select * from blog
<where>
<include refid="title-and-auther"></include>
</where>
</select>
注意,
- 最好基于单表来定义SQL片段,多表可能会出现,sql混乱
- 不要存在where标签
12.10 .Foreach
动态SQL就是在拼接SQL语句,我们只要保证SQL的正确性,按照SQL的格式,去排列就可以了。
建议先写好SQL语句,在去xml中拼接。
//查询1-3号记录的博客
List<Blog> queryBlogForeach(Map map);
原本的sql是这样
select * from mybatis.blog where (id=1 or id=2 or id=3);
<select id="queryBlogForeach" parameterType="map" resultType="Blog">
select * from mybatis.blog
<where>
<foreach collection="ids" index="id" open="and (" close=")" separator="or">
id=#{id}
</foreach>
</where>
</select>
collection是存放id的集合,取名叫ids。索引是id,open是从什么开始,close是从什么关闭,separator是分隔符。
open这里的and也可去掉不要。
测试
@Test
public void TestForeach(){
SqlSession sqlSession = MybatisUtils.getSqlSession();
BlogMapper mapper = sqlSession.getMapper(BlogMapper.class);
HashMap hashMap = new HashMap();//原本定义的是Map
ArrayList<Integer> ids = new ArrayList<Integer>();//用ArrayList存放id
ids.add(1);
ids.add(2);
ids.add(3);
ids.add(5);
hashMap.put("ids",ids);//把ids数组压如map中
List<Blog> blogs = mapper.queryBlogForeach(hashMap);
for (Blog blog:blogs
) {
System.out.println(blog);
}
sqlSession.close();
}