0%

java | 查询

xml 编写查询语句。

  • 查询所有
  • 查询详情
  • 条件查询

查询所有

mapper 接口 List<User> getUsers();

xml 映射文件

1
2
3
<select id = "selectAll" resultType = "User">
select * from user;
</select>

在上面有一个属性是 resultType,这个通常要和 ResultMap 一起说。

resultType 和 ResultMap

如果你搜索只是返回一个值,比如说 String ,或者是 int ,那你直接用 resultType 就行了。

1
2
3
4
5
6
//dao中的接口   
int countArticleThumbs();
//xml对应的
<select id ="countArticleThumbs" ResultType="int">
select count(*) from thumbs;
</select>

SQL 返回的是 int 型,那么 ResultType 定义成 int 型即可直接与 Java 进行绑定(基本数据类型默认可不写)。

如果是返回一个复杂的对象,并且,对象中的参数和数据库中的参数一致。就可以使用 ResultType

创建 User 对象, 拥有两个字段id,userName

1
2
3
4
5
6
7
8
9
User queryUser(String id);

<resultMap id="User" type="com.ssbm.ccapp.model.app.Usre">
<result column="user_name" jdbcType="VARCHAR" property="userName" />
</resultMap>

<select id="queryUser" resultMap="User">
select * from user where id = #{id}
</select>

上面的参数请参考 mybatis | xml 的 property 和 column

可以发现 User 对象,其属性 userName 和数据库中实际参数 user_name 并不一致,这个时候就不能用 resultType 了,因为,解析不上。

这个时候,就可以用 resultMapresultMap 可以对返回的参数进行配置,mybatis 可以进行驼峰自动转换(默认是关闭的),当数据库字段和Java对象字段不满足驼峰(列名不匹配),可以通过 resultMap 这里来配置,进行字段匹配。「注意,resultMap 属性 需要和 resultMap 标签结合使用」

如果不想用 resultMap 可以使用 as 别名。如

1
2
3
<select id="queryUser" resultType="User">
select id,user_name as userName from user where id = #{id}
</select>

查询详情

1
2
3
4
5
6
//dao中的接口   
User getUser(int id);
//xml对应的
<select id ="getUser" ResultType="User" parameterType = "int">
select * from user where id = #{id};
</select>
  • parameterType
    • 传参的参数类型「可以不写,因为可以找到接口里面的参数」

一个特殊情况,特殊字符,比如

1
2
3
<select id ="getUser" ResultType="User" parameterType = "int">
select * from user where id < #{id};
</select>

其中 id < #{id}; 中的 < 这个标识可能会误被认为是标签。

所以,< 有两种方式处理

  • 使用 &lt; 替代 <
  • 使用 CDATA
1
2
3
4
5
6
7
<select id ="getUser" ResultType="User" parameterType = "int">
select * from user where id
<![CDATA[
<
]]
#{id};
</select>

CDATA 区里面的内容是纯文本。

条件查询

多条件查询

接口传参一共有 3 种方式。

1
2
3
4
5
@Data
public class User{
private String name;
private String password;
}

接口的三种方式

  • 参数传递
  • 对象传递
  • Map 传递
1
2
3
4
5
List<User> getUsers1(@param("name") String name,@param("password") String password);

List<User> getUsers2(User user);

List<User> getUsers3(Map map);

相关的 xml

1
2
3
4
5
6
<select id="getUser" resultType="User">
select * from user
where
name = #{name},
and password like #{password}
</select>

动态条件查询

上面的多条件查询有一个问题,如果参数 name 不进行传参,为 null 的话,那么就查询不出来数据。

  • if
  • choose [when、otherwise]
  • trim [where、set]
  • foreach

if

1
2
3
4
5
6
7
8
9
<select id="getUser" resultType="User">
select * from user
where
<if test="name != null and name != ''">
name = #{name},
</if>

and password like #{password}
</select>

<if> 标签里面,test 写表达式,并且,里面的参数,应该和传递参数相同,如

1
2
3
<if test="nickName != null and nickName != ''">
nick_name = #{nickName},
</if>

and 情况解决。

如果 <if> 里面的标签内容不符合,那么 sql 就会变成 select * from user where and password like ? 显然不符合规范,所以,有两种方法解决上面的问题。

恒等式
1
2
3
4
5
6
7
8
9
<select id="getUser" resultType="User">
select * from user
where 1=1
<if test="name != null and name != ''">
name = #{name},
</if>

and password like #{password}
</select>
where 标签
1
2
3
4
5
6
7
8
9
10
11
<select id="getUser" resultType="User">
select * from user
<where>
<if test="name != null and name != ''">
name = #{name},
</if>
<if test="password != null">
and password like #{password}
</if>
</where>
</select>

mybatis 会自动处理这种情况。

单条件的动态查询

从多个条件中选择一个进行查询。

  • choose [when、otherwise]

类似于,图书馆查询的时候,大条件是 书名、期刊、作者、内容,小条件是具体查询的内容。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<select id="test" resultMap="Test">
select * from data
where
<choose> <!--类似 switch-->
<when test="book != null"> <!--类似 case-->
book = #{book}
</when>
<when test="vaule != null">
value = #{value}
</when>
<otherwise> <!--类似 default-->
1 = 1
</otherwise>
</choose>

</select>
请我喝杯咖啡吧~