Mybatis参数传递方法小结

Mybatis参数传递方法小结

一、 单个参数

这是最简单的情况,当 Mapper 接口方法只有一个参数时。

  • 描述: 可以是 Java 的基本类型 (int, float, boolean 等)、包装类型 (Integer, Float, Boolean 等)、String 类型,也可以是一个复杂的 Java Bean 对象 (POJO)。
  • XML 中引用: 在 XML 文件中,你可以使用 #{任意名称} 来引用这个参数。MyBatis 不关心 #{} 里面的名字是什么(虽然推荐使用有意义的名字,比如参数本身的名称)。对于 POJO 对象作为单个参数,可以直接使用#{propertyName}来引用其属性。

示例:

  • Mapper 接口:
package com.example.mapper;
import com.example.model.User;

public interface UserMapper {
    // 根据 ID 查询用户 (基本类型包装类)
    User findUserById(Integer id);

    // 根据 Email 查询用户 (String 类型)
    User findUserByEmail(String email);

    // 更新用户信息 (POJO 作为单个参数)
    int updateUserDetails(User user);
}

  • XML 映射文件 (UserMapper.xml):
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.example.mapper.UserMapper">

    <select id="findUserById" resultType="com.example.model.User">
        SELECT id, username, email FROM users WHERE id = #{userId} </select>

    <select id="findUserByEmail" resultType="com.example.model.User">
        SELECT id, username, email FROM users WHERE email = #{emailAddress} </select>

    <update id="updateUserDetails">
        UPDATE users
        SET username = #{username}, email = #{email} WHERE id = #{id}
    </update>
</mapper>

二、 多个参数

当 Mapper 接口方法有多个参数时,MyBatis 需要知道如何在 XML 中引用它们。有以下几种常用方式:

1. 使用参数索引 (不推荐)
  • 描述: 在较旧的 MyBatis 版本或者特定配置下,可以通过参数在方法签名中的顺序(从 0 开始)来引用。形式为 #{0}, #{1}… 或者 #{param1}, #{param2}…。

  • 缺点: 可读性差,容易出错,依赖于参数顺序,不推荐在现代开发中使用。MyBatis 3.4.1 默认 useActualParamNametrue,使得基于 @Param 或参数实际名称的方式成为主流。

示例 (仅作了解,不推荐使用):

  • Mapper 接口:
User findUserByNameAndDept(String name, String department);
  • XML 映射文件:
<select id="findUserByNameAndDept" resultType="com.example.model.User">
    SELECT * FROM users WHERE username = #{0} AND department = #{1}
    </select>
2.使用 @Param 注解 (推荐)
  • 描述: 这是处理多个参数最清晰、最推荐的方式。通过在 Mapper 接口方法的参数前添加 @Param(“自定义名称”) 注解,可以明确指定每个参数在 XML 中引用的名称。

  • 原理: MyBatis 会将带有 @Param 注解的参数封装到一个 Map<String, Object> 中,Map 的 key 就是 @Param 注解中指定的字符串,value 就是对应的参数值。XML 中通过 #{注解指定的名称} 来引用。

示例:

  • Mapper 接口:
import org.apache.ibatis.annotations.Param;
// ... 其他 import

public interface UserMapper {
    User findUserByNameAndDept(@Param("userName") String name, @Param("deptName") String department);
}

  • XML 映射文件:
<select id="findUserByNameAndDept" resultType="com.example.model.User">
    SELECT id, username, email, department
    FROM users
    WHERE username = #{userName} AND department = #{deptName} </select>

3. 使用 Map
  • 描述: 将所有参数放入一个 Map 对象中,然后将这个 Map 作为 单个参数 传递给 Mapper 接口方法。

  • 优点: 灵活,适用于参数个数不确定或参数较多的情况。

  • XML 中引用: 直接使用 #{mapKey} 来引用 Map 中的值。

示例:

  • Mapper 接口:
import java.util.Map;
// ... 其他 import

public interface UserMapper {
    User findUserByCriteria(Map<String, Object> criteria);
}

  • 调用代码:
Map<String, Object> params = new HashMap<>();
params.put("nameParam", "John Doe");
params.put("deptParam", "Sales");
User user = userMapper.findUserByCriteria(params);

  • XML 映射文件:
<select id="findUserByCriteria" resultType="com.example.model.User">
    SELECT id, username, email, department
    FROM users
    WHERE username = #{nameParam} AND department = #{deptParam} </select>

4. 使用 POJO (Java Bean)
  • 描述: 将所有相关的参数封装到一个自定义的 Java 对象 (POJO 或 DTO) 中,然后将这个对象作为 单个参数 传递给 Mapper 接口方法。

  • 优点: 结构清晰,代码可读性好,特别适合参数代表一个业务实体或数据传输单元的情况 (如插入、更新操作)。

  • XML 中引用: 使用 #{propertyName} 来引用 POJO 的属性。

示例:

  • Mapper 接口:
package com.example.param;

public class UserQueryParam {
    private String name;
    private String department;
    // Getters and Setters...
    // Constructor(s)...
}

  • Mapper 接口:
import com.example.param.UserQueryParam;
// ... 其他 import

public interface UserMapper {
    User findUserByPojo(UserQueryParam queryParam);
}

  • XML 映射文件:
<select id="findUserByPojo" resultType="com.example.model.User">
    SELECT id, username, email, department
    FROM users
    WHERE username = #{name} AND department = #{department} </select>

三、 List 传参
  • 描述: 当你需要传递一个列表(例如,用于 SQL 的 IN 子句)时,可以将 java.util.List 作为参数传递。

  • 处理方式: 通常在 XML 中结合 <foreach> 标签来遍历 List 中的元素。如果List是唯一的参数,可以直接在 <foreach>collection 属性中写 list;如果是多个参数中的一个,强烈建议使用 @Param List 指定一个明确的名称。

示例:

  • Mapper 接口:
import java.util.List;
import org.apache.ibatis.annotations.Param;
// ... 其他 import

public interface UserMapper {
    List<User> findUsersByIdList(@Param("userIds") List<Integer> idList);
}

  • XML 映射文件:
<select id="findUsersByIdList" resultType="com.example.model.User">
    SELECT id, username, email
    FROM users
    WHERE id IN
    <foreach item="singleId" collection="userIds" open="(" separator="," close=")">
        #{singleId}
    </foreach>
    </select>

这里foreach表示循环操作,具体的参数含义如下:

foreach元素的属性主要有 itemindexcollectionopenseparatorclose

  • item表示集合中每一个元素进行迭代时的别名,
  • index指定一个名字,用于表示在迭代过程中,每次迭代到的位置,
  • open表示该语句以什么开始,
  • separator表示在每次进行迭代之间以什么符号作为分隔符,
  • close表示以什么结束

注意:

在使用foreach的时候最关键的也是最容易出错的就是collection属性,该属性是必须指定的,但是在不同情况下,该属性的值是不一样的,主要有一下3种情况:

  1. 如果传入的是单参数且参数类型是一个List的时候,collection属性值为list
  2. 如果传入的是单参数且参数类型是一个array数组的时候,collection的属性值为array
  3. 如果传入的参数是多个的时候,我们就需要把它们封装成一个Map或者Object
四、 数组传参
  • 描述:List 类似,也可以传递数组作为参数,常用于 IN 子句。

  • 处理方式:List 非常相似,同样在 XML 中使用 <foreach> 标签。如果数组是唯一参数,collection 属性可以直接写 array;如果是多个参数之一,也强烈建议使用 @Param 命名。

示例:

  • Mapper 接口:
import org.apache.ibatis.annotations.Param;
// ... 其他 import

public interface UserMapper {
    List<User> findUsersByIdArray(@Param("idArray") Integer[] ids);
}

  • XML 映射文件:
<select id="findUsersByIdArray" resultType="com.example.model.User">
    SELECT id, username, email
    FROM users
    WHERE id IN
    <foreach item="idElement" collection="idArray" open="(" separator="," close=")">
        #{idElement}
    </foreach>
    </select>

五、总结与建议
  • 单个参数: 直接传递,XML 中用 **#{任意名称} **或 #{propertyName} (对于 POJO)
  • 多个简单参数: 强烈推荐使用 @Param 注解为每个参数命名,XML 中用 #{注解名}
    • 多个相关参数/结构化参数: 推荐封装成 POJO 或使用 Map 传递,XML 中用 #{propertyName}#{mapKey}
    • 集合参数 (List/数组): 使用 @Param 命名(尤其是有其他参数时),在 XML 中结合 <foreach> 标签处理。
    • 避免使用 索引传参 (#{0}, #{param1}) 的方式。

选择哪种方式取决于参数的数量、性质以及个人或团队的编码风格偏好。通常,清晰性和可维护性是首要考虑因素,因此 @Param POJO 是最常用的方式

参考:

  1. MyBatis 的几种传参方式,看完就懂了!
  2. Mybatis中传递多个参数的4种方法
  3. 三、MyBatis实践:提高持久层数据处理效率
  4. mybatis 传递参数的7种方法
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值