1 MyBatis动态SQL之综述和 if 语句

摘要:使用 MyBatis 动态SQL,通过 if, choose, when, otherwise, trim, where, set, foreach和bind等标签,可组合成非常灵活的SQL语句,从而既提高 SQL 语句的准确性,也大大提高攻城狮的开关效率。

1 MyBatis动态SQL之if 语句
2 MyBatis动态sql之where标签|转
3 MyBatis动态SQL之set标签|转
4 MyBatis动态SQL之trim元素|转
5 MyBatis动态sql中foreach标签的使用
6 MyBatis动态SQL之choose(when、otherwise)语句
7 MyBatis动态SQL之bind标签|转

综述

  动态 SQL 是 MyBatis 的强大特性之一。如果你使用过 JDBC 或其它类似的框架,你应该能理解根据不同条件拼接 SQL 语句有多痛苦,例如拼接时要确保不能忘记添加必要的空格,还要注意去掉列表最后一个列名的逗号。利用动态 SQL,可以彻底摆脱这种痛苦。

  使用动态 SQL 并非一件易事,但MyBatis 3 基于功能强大的 OGNL 表达式借助可用于任何 SQL 映射语句中的、强大的动态 SQL 语言,显著地提升了这一特性的易用性。

OGNL,全称为Object-Graph Navigation Language,它是一个功能强大的表达式语言,用来获取和设置Java对象的属性,它旨在提供一个更高的更抽象的层次来对Java对象图进行导航。

  如果你之前用过 JSTL 或任何基于类 XML 语言的文本处理器,你对动态 SQL 元素可能会感觉似曾相识。MyBatis 3 常用的动态SQL元素包括:

  • if
  • where
  • set
  • trim
  • foreach
  • choose (when、otherwise)

  下面我们就用一个简单示例来看看在MyBatis中怎么使用动态SQL。

定义表结果和实体类

  首先,在数据库创建一个表tb_employee,并插入测试数据。SQL脚本如下:

CREATE TABLE tb_employee(
ID INT(11) PRIMARY KEY AUTO_INCREMENT,
loginname VARCHAR(18),
PASSWORD VARCHAR(18),
NAME VARCHAR(18) DEEAULT NULL,
SEX CHAR(2) DEEAULT NULL,
AGE INT(11) DEFAULT NULL,
phone VARCHAR(21),
sal DOUBLE,
state VARCHAR(18)
);
INSERT INTO tb_employee(loginname,PASSWORD,NAMB,sex,age,phone,sal,state
VALUES('jack','123456','楼兰胡杨",'男',26,'13900000001',9800,'ACTIVE');
INSERT INTO tb_employee (loginname,PASSWORD,NAMB,sex,age,phone,sal,state)
VALUES('rose','123456','Wiener','女',21,'13900000002',6800,'ACTIVE');
INSERT INTO tb_employee (loginname,PASSWORD,NAME,sex,age,phone,sal,state)
VALUES('tom','123456','汤姆','男',25,'13900000003,8800,'ACTIVE');
INSERT INTO tb_employee (loginname,PASSWORD,NAME sex,age,phone,sal,state)
VALUES('alice','123456','爱丽丝','女’,20,'13900000004,5800,ACTIVE');

  在数据库中执行SQL 脚本,完成创建tb_employee的操作。用实体类Employee映射tb_employee表。tb_employee 和 mployee将贯穿动态SQL所有章节。

if语句

  动态SQL通常会做的事情是有条件地包含where子句的一部分。比如:

<select id="selectEmployeeById" resultType="cn.mybatis.domain.Employee">
SELECT * FROM tb_employee WHERE state = 'ACTIVE'
<!-- 可选条件,如果传进来的参数有id属性,则加上id查询条件-->
<if test="id != null">
and id = #{id}
</if>
</select>

  假设在上述SQL中查询条件id的值不为null,那么控制台打印出来的SQL为:

SBLECT * EROM tb_employee WHERE state = 'ACTIVE' and id = ?

  以上语句提供了一个可选的、根据id查找Employee的功能。如果没有传入id,那么所有处于“ACTIVE”状态的Employee都会被返回; 反之若传入了id,那么就会把查找id内容的Employee结果返回。如果想通过两个条件搜索该怎么办呢? 很简单,只要多加入一个条件即可,例如:

<select id="selectEmployeeByIdLike" resultType="cn.mybatis.domain.Employee">
SELECT * FROM tb_employee WHERE state = 'ACTIVE'
<!-- 可选条件,如果传进来的参数有id属性,则加上id查询条件-->
<if test="id != null">
and id = #{id}
</if>
<!-- 两个可选条件,例如登录功能的登录名和密码查询-->
<if test="loginname != null and password != null">
and loginname = #{loginname} and password = #{password)
</if>
</select>

可以使用两个等于号==判断id等于null的场景,if语句示例如下:

<if test="id == null">

  如果不使用if语句,则其SQL脚本如下:

<select id="selectByName" resultType="cn.mybatis.domain.Employee">
    <!-- 这和普通的sql 查询语句十分相似 -->
    select * from tb_employee WHERE state = 'ACTIVE'and id = #{id} and loginname=#{loginname} and password=#{password}
</select>

  我们从上面的查询语句可以发现,如果 #{loginname} 为空,那么查询结果也是空,使用起来缺乏灵活性,而动态SQL完全不畏惧这个。这就是动态SQL的长处之所在。

Reference

posted @ 2022-03-30 08:02  楼兰胡杨  阅读(216)  评论(0编辑  收藏  举报