MyBatis——dao代理的使用、深入理解参数(传递一个参数、传递多个参数、使用entity实体类传递、使用自定义类传递、按位置传递、使用Map传递)

简介: MyBatis——dao代理的使用、深入理解参数(传递一个参数、传递多个参数、使用entity实体类传递、使用自定义类传递、按位置传递、使用Map传递)

文章目录:


1.MyBatisdao代理

1.1 MyBatis提供代理 

1.2 使用MyBatis代理的要求 

1.3 MyBatis代理的实现方式

2.深入理解相关参数

2.1 parameterType

2.2 dao接口的方法形参列表中只有一个参数(重要!!!)

2.3 dao接口的方法形参列表中有多个参数(重要!!!)

2.4 dao接口的方法形参列表中使用entity实体类对象(重要!!!)

2.5 dao接口的方法形参列表中使用自定义类对象(重要!!!)

2.6 dao接口的方法形参列表中按位置传递参数(不推荐!!!)

2.7 dao接口的方法形参列表中按Map传递参数(不推荐!!!)

写在结尾

1.MyBatis的dao代理


1.1 MyBatis提供代理 

MyBatis创建 dao 接口的实现类对象,完成对 sql 语句的执行。也就是说,MyBatis会创建一个对象代替你的 dao 实现类的功能。


1.2 使用MyBatis代理的要求 

1.    mapper文件中的 namespace 一定是 dao 接口的全限定名称。

2.    mapper文件中标签的 id 属性值必须是 dao 接口的方法名称。 


1.3 MyBatis代理的实现方式

使用 SqlSession 对象的方法 getMapper(dao.class),在这里通过Java反射机制,来获取对应的 dao 接口中的相关内容。 

    @Test
    public void testSelectById() {
        //1.获取SqlSession
        SqlSession session = MyBatisUtil.getSqlSession();
        //2.获取dao的代理
        StudentDao studentDao=session.getMapper(StudentDao.class);
        Student student=studentDao.selectById(1001);
        System.out.println("student = " + student);
        //3.关闭SqlSession对象
        session.close();
    }

    @Test
    public void testSelectStudents() {
        SqlSession session=MyBatisUtil.getSqlSession();
        StudentDao studentDao=session.getMapper(StudentDao.class);
        //com.sun.proxy.$Proxy == StudentDaoImpl
        System.out.println("studentDao === " + studentDao.getClass().getName());
        List<Student> students=studentDao.selectStudents();
        students.forEach( stu-> System.out.println("stu = " + stu));
        session.close();
    }

在上面两个测试方法中,有等价的代码如下:👇👇👇

1.  StudentDao studentDao=session.getMapper(StudentDao.class);

2.  //等同于

3.  StudentDao studentDao=new StudentDaoImpl();

2.深入理解相关参数


理解参数就是:通过Java程序把数据传入到 mapper 文件中的 sql 语句。参数主要是指 dao 接口中方法的形参。

下面先给出MyBatis支持的Java类型的别名!!!

上图中,列表的左边为MyBatis支持的Java类型的别名,右边为通过反射机制得到的Java中的映射数据类型。 


2.1 parameterType

有关 parameterType 的理解,可以参考下面xml文件中的注释部分。

package com.bjpowernode.dao;
import com.bjpowernode.entity.Student;
import java.util.List;
/**
 *
 */
public interface StudentDao {
    Student selectById(Integer id);
}
    <!--
        parameterType: 指定dao接口形参的类型
        这个属性的值可以使用 java 类型的全限定名称或者 mybatis定义的别名
        mybatis执行的sql语句:select id,name,email,age from student where id=?
        ? 是占位符,使用jdbc中的PreparedStatement执行这样的sql语句
        PreparedStatement pst=conn.preparedStatement("select id,name,email,age from student where id=?");
        给 ? 位置赋值
        参数Integer:执行pst.setInt(1,1001);  对应了mybatis中的 parameterType="java.lang.Integer"
        参数String:执行pst.setString(1,"1001");
        第一个用法:java类型的全限定名称 parameterType="java.lang.Integer"
        第二个用法:mybatis定义的java类型的别名 parameterType="intinteger"
        mybatis通过反射机制可以获取 dao 接口方法的参数类型,即parameterType可以不写
    -->
    <select id="selectById" parameterType="integer"
            resultType="com.bjpowernode.entity.Student">
        select id,name,email,age from student where id=#{studentId}
    </select>
    @Test
    public void testSelectById() {
        //1.获取SqlSession
        SqlSession session = MyBatisUtil.getSqlSession();
        //2.获取dao的代理
        StudentDao studentDao=session.getMapper(StudentDao.class);
        Student student=studentDao.selectById(1003);
        System.out.println("student = " + student);
        //3.关闭SqlSession对象
        session.close();
    }

可以看到在输出结果中,出现了 Parameters 这一项,就是说参数类型是 Integer


2.2 dao接口的方法形参列表中只有一个参数(重要!!!)

package com.bjpowernode.dao;
import com.bjpowernode.entity.Student;
import java.util.List;
/**
 *
 */
public interface StudentDao {
    //dao接口的方法形参是一个简单类型
    //简单类型:java基本数据类型和String
    Student selectByEmail(String email);
}
    <!--
        dao接口是一个简单类型的参数(java 基本类型和 String)
        mapper文件获取这个参数值:使用 #{任意字符}
    -->
    <select id="selectByEmail" resultType="com.bjpowernode.entity.Student">
        select id,name,email,age from student where email=#{studentEmail}
    </select>
    @Test
    public void testOneParameter() {
        SqlSession session=MyBatisUtil.getSqlSession();
        StudentDao studentDao=session.getMapper(StudentDao.class);
        Student student=studentDao.selectByEmail("zhangsan@qq.com");
        System.out.println("email === " + student);
        session.close();
    }

2.3 dao接口的方法形参列表中有多个参数(重要!!!)

package com.bjpowernode.dao;
import com.bjpowernode.entity.Student;
import org.apache.ibatis.annotations.Param;
import java.util.List;
/**
 *
 */
public interface StudentDao {
    /*
     *  多个简单类型的参数
     *  使用 @Param 命名参数,注解都是mybatis提供的
     *  位置:在形参定义的前面
     *  属性:value 自定义的参数名称
     */
    List<Student> selectByNameOrAge(@Param("myname") String name,
                                    @Param("myage") Integer age);
}
    <!--
        多个简单类型的参数
        当你使用了 @Param 命名后,例如 @param("myname")
        在mapper中,使用 #{命名的参数},即 #{myname}
    -->
    <select id="selectByNameOrAge" resultType="com.bjpowernode.entity.Student">
        select id,name,email,age from student where name=#{myname} or age=#{myage}
    </select>
    @Test
    public void testSelectByNameOrAge() {
        SqlSession session=MyBatisUtil.getSqlSession();
        StudentDao studentDao=session.getMapper(StudentDao.class);
        List<Student> students=studentDao.selectByNameOrAge("张三",20);
        students.forEach( stu-> System.out.println("stu = " + stu));
        session.close();
    }

2.4 dao接口的方法形参列表中使用entity实体类对象(重要!!!)

package com.bjpowernode.dao;
import com.bjpowernode.entity.Student;
import java.util.List;
/**
 *
 */
public interface StudentDao {
    /*
     *  一个java对象作为参数(对象有属性,每个属性有set、get方法)
     */
    List<Student> selectByObject(Student student);
}
<!--
    一个java对象作为方法的参数,使用对象的属性作为参数值
    简单的语法:#{属性名},mybatis调用此属性的getXXX()方法
-->
<select id="selectByObject" resultType="com.bjpowernode.entity.Student">
    select id,name,email,age from student where name=#{name} or age=#{age}
</select>
<!--
    也可以写成下面这种复杂的更详细的格式:
    javaType=java中数据类型名
    jdbcType=数据库中数据类型名称
-->
<select id="selectByObject" resultType="com.bjpowernode.entity.Student">
    select id,name,email,age
    from student
    where name=#{name,javaType=java.lang.String,jdbcType=VARCHAR} or
          age=#{age,javaType=java.lang.Integer,jdbcType=INTEGER}
</select>
    @Test
    public void testSelectByObject() {
        SqlSession session=MyBatisUtil.getSqlSession();
        StudentDao studentDao=session.getMapper(StudentDao.class);
        Student student=new Student();
        student.setName("张三");
        student.setAge(20);
        List<Student> students=studentDao.selectByObject(student);
        students.forEach( stu-> System.out.println("stu = " + stu));
        session.close();
    }

2.5 dao接口的方法形参列表中使用自定义类对象(重要!!!)

首先,我们新建一个自定义类,如下图:👇👇👇 

package com.bjpowernode.vo;
/**
 *
 */
public class QueryParam {
    private Object p1;
    private Object p2;
    public Object getP1() {
        return p1;
    }
    public void setP1(Object p1) {
        this.p1 = p1;
    }
    public Object getP2() {
        return p2;
    }
    public void setP2(Object p2) {
        this.p2 = p2;
    }
}
package com.bjpowernode.dao;
import com.bjpowernode.entity.Student;
import com.bjpowernode.vo.QueryParam;
import java.util.List;
/**
 *
 */
public interface StudentDao {
    List<Student> selectByQueryParam(QueryParam param);
}
<select id="selectByQueryParam" resultType="com.bjpowernode.entity.Student">
    select id,name,email,age from student where name=#{p1} or age=#{p2}
</select>


    @Test
    public void testSelectByObject2() {
        SqlSession session=MyBatisUtil.getSqlSession();
        StudentDao studentDao=session.getMapper(StudentDao.class);
        QueryParam param=new QueryParam();
        param.setP1("李四");
        param.setP2(15);
        List<Student> students=studentDao.selectByQueryParam(param);
        students.forEach( stu-> System.out.println("stu = " + stu));
        session.close();
    }

2.6 dao接口的方法形参列表中按位置传递参数(不推荐!!!)

参数位置:dao接口中方法的形参列表,从左到右,参数位置是:012......

package com.bjpowernode.dao;
import com.bjpowernode.entity.Student;
import java.util.List;
/**
 *
 */
public interface StudentDao {
    //使用位置获取参数
    List<Student> selectByPosition(String name,Integer age);
}
<!--
    使用位置获取参数值,dao接口方法是多个简单类型的参数
    语法:#{arg0},#{arg1}...
-->
<select id="selectByPosition" resultType="com.bjpowernode.entity.Student">
    select id,name,email,age from student where name=#{arg0} or age=#{arg1}
</select>
    @Test
    public void testSelectByPosition() {
        SqlSession session=MyBatisUtil.getSqlSession();
        StudentDao studentDao=session.getMapper(StudentDao.class);
        List<Student> students=studentDao.selectByPosition("张三",15);
        students.forEach( stu-> System.out.println("stu = " + stu));
        session.close();
    }

2.7 dao接口的方法形参列表中按Map传递参数(不推荐!!!)

package com.bjpowernode.dao;
import com.bjpowernode.entity.Student;
import java.util.List;
import java.util.Map;
/**
 *
 */
public interface StudentDao {
    //使用Map作为参数
    List<Student> selectStudentByMap(Map<String,Object> map);
}
<!--
    使用Map传递参数
    在mapper文件中,获取map的值,是通过key获取的,语法:#{key}
-->
<select id="selectStudentByMap" resultType="com.bjpowernode.entity.Student">
    select id,name,email,age from student where name=#{myname} or age=#{myage}
</select>
    @Test
    public void testSelectByMap() {
        SqlSession session=MyBatisUtil.getSqlSession();
        StudentDao studentDao=session.getMapper(StudentDao.class);
        Map<String,Object> map=new HashMap<>();
        map.put("myname","张三");
        map.put("myage",20);
        List<Student> students=studentDao.selectStudentByMap(map);
        students.forEach( stu-> System.out.println("stu = " + stu));
        session.close();
    }


写在结尾


上面的所有实例,给出的代码都是这几块:

1.    dao接口中的相关方法体

2.    mapper文件中的相关标签(每个标签对应着 dao 接口中的一个方法体)

3.    测试类中的测试方法(每个测试方法对应着 dao 接口中某个方法体的具体实现)

4.    程序的运行结果

推荐大家使用 2.22.32.42.5 这几种方法来传递参数!!!

在这里就不再给出 mybatis.xml 主配置文件了,因为其中的数据源、读取mapper文件的标签内容都是不做修改的。

相关文章
|
6月前
|
SQL XML Java
8、Mybatis-Plus 分页插件、自定义分页
这篇文章介绍了Mybatis-Plus的分页功能,包括如何配置分页插件、使用Mybatis-Plus提供的Page对象进行分页查询,以及如何在XML中自定义分页SQL。文章通过具体的代码示例和测试结果,展示了分页插件的使用和自定义分页的方法。
8、Mybatis-Plus 分页插件、自定义分页
|
6月前
|
SQL Java 测试技术
3、Mybatis-Plus 自定义sql语句
这篇文章介绍了如何在Mybatis-Plus框架中使用自定义SQL语句进行数据库操作。内容包括文档结构、编写mapper文件、mapper.xml文件的解释说明、在mapper接口中定义方法、在mapper.xml文件中实现接口方法的SQL语句,以及如何在单元测试中测试自定义的SQL语句,并展示了测试结果。
3、Mybatis-Plus 自定义sql语句
|
6月前
|
SQL Java Kotlin
MybatisPlus怎么拓展自定义BaseMapper
通过扩展Mybatis-Plus的`BaseMapper`,可以自定义SQL模板以满足特定业务需求。例如,当遇到唯一键冲突而不希望抛出异常时,可使用`INSERT IGNORE`语法。首先,创建`InsertIgnore`类继承`AbstractMethod`并定义`insertIgnore`方法及其SQL模板。接着,在自定义的`UltraBaseMapper`接口中声明`insertIgnore`方法,并让业务Mapper继承此接口。最后,通过`UltraSqlInjector`类将`InsertIgnore`方法注册到Mybatis-Plus插件中。
239 1
|
3月前
|
SQL 缓存 Java
【详细实用のMyBatis教程】获取参数值和结果的各种情况、自定义映射、动态SQL、多级缓存、逆向工程、分页插件
本文详细介绍了MyBatis的各种常见用法MyBatis多级缓存、逆向工程、分页插件 包括获取参数值和结果的各种情况、自定义映射resultMap、动态SQL
【详细实用のMyBatis教程】获取参数值和结果的各种情况、自定义映射、动态SQL、多级缓存、逆向工程、分页插件
|
4月前
|
SQL Java 数据库连接
mybatis使用四:dao接口参数与mapper 接口中SQL的对应和对应方式的总结,MyBatis的parameterType传入参数类型
这篇文章是关于MyBatis中DAO接口参数与Mapper接口中SQL的对应关系,以及如何使用parameterType传入参数类型的详细总结。
86 10
|
5月前
|
SQL XML Java
mybatis复习02,简单的增删改查,@Param注解多个参数,resultType与resultMap的区别,#{}预编译参数
文章介绍了MyBatis的简单增删改查操作,包括创建数据表、实体类、配置文件、Mapper接口及其XML文件,并解释了`#{}`预编译参数和`@Param`注解的使用。同时,还涵盖了resultType与resultMap的区别,并提供了完整的代码实例和测试用例。
mybatis复习02,简单的增删改查,@Param注解多个参数,resultType与resultMap的区别,#{}预编译参数
|
6月前
|
JavaScript 前端开发
Vue中传递自定义参数到后端、后端获取数据(使用Map接收参数)
这篇文章讲述了如何在Vue中通过Axios二次封装传递自定义参数到后端,并展示了后端如何使用Map接收这些参数,以及如何避免参数转换错误和统一接口设计的方法。
|
7月前
|
SQL Java 数据库连接
idea中配置mybatis 映射文件模版及 mybatis plus 自定义sql
idea中配置mybatis 映射文件模版及 mybatis plus 自定义sql
170 3
|
7月前
|
Java 数据库连接 mybatis
Mybatis查询传递单个参数和传递多个参数用法
Mybatis查询传递单个参数和传递多个参数用法
104 11
|
7月前
|
Java 数据库连接 Maven
文本,使用SpringBoot工程创建一个Mybatis-plus项目,Mybatis-plus在编写数据层接口,用extends BaseMapper<User>继承实体类
文本,使用SpringBoot工程创建一个Mybatis-plus项目,Mybatis-plus在编写数据层接口,用extends BaseMapper<User>继承实体类