动态SQL
SQL语句是变化的
有些时候我们需要进行分类筛选信息,这个时候就不适合将 sql 语句写死,而是需要通过不同的的功能需求来拼接不同的 sql 语句,这个时候就需要用到我们的动态SQL了
动态SQL的标签
标签 | 作用 |
---|---|
if标签 | 条件判断,但条件判断,如果有多个的话,在前面加上and |
where标签 | 让where子句更加动态智能 |
trim标签 | 通过不同属性简化条件语句 |
set标签 | 主要使用在update语句当中,用来生成set关键字,同时去掉最后多余的“,” |
choose when otherwise标签 | 三个标签连在一起使用,相当于if-else if-else,只有一个分支会进行 |
foreach标签 | 循环数组或集合,动态生成sql |
sql标签与include标签 | 代码复用,易维护 |
各个标签的功能详细介绍
1、if标签:
筛选条件语句
多条件查询,通过品牌、价格、类型进行查询
<!--在CarMapper.xml文件中编写的sql语句;
这里select * 虽然mysql数据库表中的字段名和属性类中的属性名不一致,
但是开启了驼峰命名自动映射,所以不需要编写别名-->
<!--where 1=1这个是为了适应每个if标签前面的and,使sql语句不报错-->
<select id="selectByBrand" resultType="car">
select * from t_car where 1=1
<if test="brand!=null and brand!=''">
and brand like "%"#{brand}"%"
</if>
<if test="guidePrice!=null and guidePrice!=''">
and guide_price >= #{guidePrice}
</if>
<if test="carType!=null and carType!=''">
and car_type=#{carType}
</if>
</select>
//在CarMapper的接口中编写的方法
//使用注解标明参数名称,便于后面xml中的sql语句编写
List<Car> selectByBrand(@Param("brand") String brand, @Param("guidePrice") Double guidePrice, @Param("carType") String carType);
@Test
//测试代码
public void testSelectByBrand(){
SqlSession sqlSession = SqlSessionUtil.openSession();
CarMapper mapper = sqlSession.getMapper(CarMapper.class);
// List<Car> lists= mapper.selectByBrand("奔驰",2.0,"新能源");所有条件都不为空
// List<Car> lists= mapper.selectByBrand(null,2.0,"新能源");第一个条件为空
List<Car> lists= mapper.selectByBrand(null,null,"新能源");
lists.forEach(list -> System.out.println(list));
sqlSession.close();
}
2、where标签
where标签的作用:让where子句更加动态智能。
- 所有条件都为空时,where标签保证不会生成where子句
- 自动去除某些条件前面多余的and或or
- 但是不能自动去掉后面多余的and或or
<select id="selectByWhere" resultType="car">
select * from t_car
<where>
<if test="brand!=null and brand!=''">
and brand like "%"#{brand}"%"
</if>
<if test="guidePrice!=null and guidePrice!=''">
and guide_price >= #{guidePrice}
</if>
<if test="carType!=null and carType!=''">
and car_type=#{carType}
</if>
</where>
</select>
3、trim标签
trim标签的属性:
- prefix:在trim标签中的语句前添加内容
- suffix:在trim标签中的语句后添加内容
- prefixOverrides:前缀覆盖掉(去掉)
- suffixOverrides:后缀覆盖掉(去掉)
如果条件全为空时,where子句不会被添加上去
<!--使用了suffixOverrides在后面添加and-->
<select id="selectByTrim" resultType="car">
select * from t_car
<trim prefix="where" suffixOverrides="and|or">
<if test="brand!=null and brand!=''">
brand like "%"#{brand}"%" and
</if>
<if test="guidePrice!=null and guidePrice!=''">
guide_price >= #{guidePrice} and
</if>
<if test="carType!=null and carType!=''">
car_type=#{carType}
</if>
</trim>
</select>
4、set标签
主要使用在update语句当中,用来生成set关键字,同时去掉最后多余的“,”
比如我们只更新提交的不为空的字段,如果提交的数据是空或者"",那么这个字段我们将不更新。
<update id="updateWithSet">
update t_car
<set>
<if test="carNum != null and carNum != ''">car_num = #{carNum},</if>
<if test="brand != null and brand != ''">brand = #{brand},</if>
<if test="guidePrice != null and guidePrice != ''">guide_price = #{guidePrice},</if>
<if test="produceTime != null and produceTime != ''">produce_time = #{produceTime},</if>
<if test="carType != null and carType != ''">car_type = #{carType},</if>
</set>
where id=#{id}
</update>
5、choose when otherwise
三个标签在一起使用,只有一个分支可以执行,类似于分支语句中的if-else if -else
<!--语法格式-->
<choose>
<when></when>
<when></when>
<when></when>
<otherwise></otherwise>
</choose>
choose标签是按顺序判断其内部when标签中的test条件出否成立,如果有一个成立,则 choose 结束。当 choose 中所有 when 的条件都不满则时,则执行 otherwise 中的sql。类似于Java 的 switch 语句,choose 为 switch,when 为 case,otherwise 则为 default。
<select id="selectWithChoose" resultType="car">
select * from t_car
<where>
<choose>
<when test="brand!=null and brand!=''">
brand like "%"#{brand}"%"
</when>
<when test="guidePrice !=null and guidePrice !=''">
guidePrice >=#{guidePrice}
</when>
<otherwise>
car_type=#{carType}
</otherwise>
</choose>
</where>
</select>
6、foreach标签
循环数组或集合,动态生成sql
批量删除
批量添加
foreach的属性
- collection:集合或数组
- item:集合或数组中的元素,即foreach需要进行遍历的对象
- separator:分隔符
- open:foreach标签中所有内容的开始
- close:foreach标签中所有内容的结束
批量删除
<!--这种方法就相当于是使用delete from t_car where id in (?,?,?)-->
<delete id="deleteFoeEach">
delete from t_car where id in
<foreach collection="ids" item="id" separator="," open="(" close=")">
#{id}
</foreach>
</delete>
<!--这个就类似于delete from t_car where id=? or id=? or id=? or id=? 通过or进行批量删除-->
<delete id="deleteFoeEachOr">
delete from t_car where
<foreach collection="ids" item="id" separator="or">
id=#{id}
</foreach>
</delete>
批量添加
<insert id="insertBatchByForeach">
insert into t_car values
<foreach collection="cars" item="car" separator=",">
(null,#{car.carNum},#{car.brand},#{car.guidePrice},#{car.produceTime},#{car.carType})
</foreach>
</insert>
7、sql标签与include标签
sql标签用来声明sql片段
include标签用来将声明的sql片段包含到某个sql语句当中
作用:代码复用。易维护。
<sql id="carCols">id,car_num carNum,brand,guide_price guidePrice,produce_time produceTime,car_type carType</sql>
<select id="selectAllRetMap" resultType="map">
select <include refid="carCols"/> from t_car
</select>
<select id="selectAllRetListMap" resultType="map">
select <include refid="carCols"/> carType from t_car
</select>
<select id="selectByIdRetMap" resultType="map">
select <include refid="carCols"/> from t_car where id = #{id}
</select>