【Mybatis】MyBatis 中参数传递的基本方式

1.案例

结合案例进行学习,案例准备如下

(1)创建一个books表如下

(2)编写BooksMapper接口

package com.its.mapper;

import com.its.pojo.Books;
import org.apache.ibatis.annotations.Param;

import java.util.List;

public interface BooksMapper {
    List<Books> selectBooksByTitle(String title);
    List<Books> selectBooksByTitleAndAuthor(String title,int bookId,String author);
    List<Books> selectBooksByTitleAndAuthor(@Param("title") String title, @Param("bookId") int bookId);
    List<Books> selectBooksByBean(Books books);
    List<Books> selectBooksByLikeTitle(@Param("title") String title);

}

编写BooksMapper.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.its.mapper.BooksMapper">

    <select id="selectBooksByTitle" resultType="com.its.pojo.Books">
        select * from demo_test.books where title = #{title}
    </select>
    <select id="selectBooksByTitleAndAuthor" resultType="com.its.pojo.Books">
        select * from demo_test.books where title = #{param1} and book_id = #{param2}
    </select>
    <select id="selectBooksByBean" resultType="com.its.pojo.Books">
        select * from demo_test.books where title = #{title} and book_id = #{bookId}
    </select>
    <select id="selectBooksByLikeTitle" resultType="com.its.pojo.Books">
        select * from demo_test.books where title like concat('%',#{title},'%')
    </select>
</mapper>

在mybatis配置文件中添加映射关系

<!--映射文件的位置-->
    <mappers>
        <mapper resource="com/its/mapper/UserMapper.xml"/>
        <mapper resource="com/its/mapper/BooksMapper.xml"/>
    </mappers>

接下来编写测试文件如下:

package com.its;

import com.its.mapper.BooksMapper;
import com.its.pojo.Books;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;

import java.io.IOException;
import java.io.InputStream;
import java.util.List;

public class BooksMapperTest {
    /*1.普通参数,单个参数,注意单个参数的传参,无论传的是啥,是否和方法的参数名一样无关,都能成功。
    这是因为实际上映射文件就是这个接口的实现类对象,执行的查询就是重写了这个接口中的方法,所以这个方法中的参数
    是可以自定义的,因此一个参数的时候你写啥都可以。
    */
    @Test
    public void books01(){
        BooksMapper mapper = session.getMapper(BooksMapper.class);
        List<Books> booksList = mapper.selectBooksByTitle("活着");
        booksList.forEach(System.out::println);
    }
    /*
     2.普通参数,两个参数的时候,就不能乱写了,因为不能识别你写的是两个参数中的那一个,这时你有三种方法传参
     (1)使用arg0 和 arg1 ...只能按着顺序从小到大,要是从大到小也能运行,但是参数会反过来,查询不到结果。
     (2)使用param1,param2 ...同上
     (3)使用@Param("指定参数名")指定参数名字,调用的时候可以直接使用指定的参数名

     */
    @Test
    public void books02(){
        BooksMapper mapper = session.getMapper(BooksMapper.class);
        List<Books> booksList = mapper.selectBooksByTitleAndAuthor("活着",1);

        booksList.forEach(System.out::println);
    }
    /*
    3.传递一个对象,直接写对象的属性名和表的字段名对应即可
    */
    @Test
    public void books03(){
        BooksMapper mapper = session.getMapper(BooksMapper.class);
        Books books = new Books();
        books.setTitle("活着");
        books.setBookId(1);
        List<Books> booksList = mapper.selectBooksByBean(books);
        booksList.forEach(System.out::println);
    }
    /*
    * 4.模糊查询,用concat()函数进行拼接,不能用'%#{}%'
    * */
    @Test
    public void books04(){
        BooksMapper mapper = session.getMapper(BooksMapper.class);

        List<Books> booksList = mapper.selectBooksByLikeTitle("着");
        booksList.forEach(System.out::println);
    }
    /*
    * 5.$ 和 # 的区别
    * 区别:$ 不会预编译 有SQL注入的风险 # 可以预编译
    * */


    SqlSession session;
    //@Before这个注解会在@Tset注解运行之前执行
    @Before //因为每一个测试时都需要有这步操作,所以统一写在这里,减少代码量
    public void init() throws IOException {
        //读取核心配置文件信息
        InputStream is = Resources.getResourceAsStream("mybatis.xml");
        //获取一个SqlSessionFactory 数据库会话工厂
        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(is);
        session = sqlSessionFactory.openSession();
    }
    //@After这个注解会在@Tset注解运行之后执行,通常用于释放资源等
    @After
    public void destroy(){
        session.close();
    }
}

2.单个方式传参

  • 当只有一个参数时,可以直接使用 #{parameter} 的形式来引用参数。

【注意】

  单个参数的传参,无论传的是啥,是否和方法的参数名一样无关,都能成功。
  这是因为实际上映射文件就是这个接口的实现类对象,执行的查询就是重写了这个接口中      的方法,所以这个方法中的参数是可以自定义的,因此一个参数的时候你写啥都可以。

 测试代码

映射文件中的SQL语句,与接口的参数名一样

执行测试代码,结果正常查询。

 

下面,将映射文件中的SQL语句中的参数与接口的参数名设置不一样

结果依然正确

3.多个参数传参

两个参数的时候,就不能乱写了,因为不能识别你写的是两个参数中的那一个,这时你有三种方法传参
(1)使用 arg0 和 arg1 ...  只能按着顺序从小到大,要是从大到小也能运行,但是参数会反过来,查询不到结果。
(2)使用param1,param2 ... 同上
(3)使用@Param("指定参数名")指定参数名字,调用的时候可以直接使用指定的参数名

代码测试1(错误传参)

接口方法

映射的sql 语句

执行测试代码,结果报错,不能识别参数。

【注意】尽管这里sql 语句中的#{ } 里设置的和接口参数一致,但也不能被识别,因为并不能确定对应的参数。

代码测试2(用arg0 和 arg1

接口方法和上面一样,在sql 语句中用上arg0 和 arg1 .......接收。

执行测试代码,结果如下,能正常识别,结果正确。

说明能够识别参数,参数是按照顺序传递进来的,如果将顺序反过来写,arg2,arg1,arg0 ,也能运行,但是,接受的参数会乱序,查询不到结果,会出现book_id = 书名,而 author = bookId 的结果。

代码测试3 (用@Param(" ")注解 )

只要在写接口的时候写上@Param("自定义的名字"),就可以在sql中引用自己定义的名字

这里现在就可以使用了。测试结果正确。

4.对象传参

如果参数是一个对象(比如实体类),可以直接传递整个对象。在 SQL 映射文件中,可以通直接写对象的属性进行传递,mybatis会自动映射到数据库的字段名。(前提是表的字段名和对象除了驼峰命名不一致,其他都一样)

代码测试

1.mapper接口方法

2.sql映射语句

3.执行测试代码,结果正确

  • 8
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值