栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

Day65.MyBatis:Mapper代理、#{} ${}传参、实体类别名、数据输入|输出(resultType)、映射关系

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

Day65.MyBatis:Mapper代理、#{} ${}传参、实体类别名、数据输入|输出(resultType)、映射关系

目录

一、MyBatis单表开发 - Mapper代理接口方式 (@Before、@After)

二、给SQL语句传参的两种方式 #{}  ${} 、模糊查询(Like)

使用 #{} ${} 实现模糊查询

三、给实体类起别名,方便resultType使用

四、数据输入

1.单个简单参数(Integer、Double、String)

2.单个引用参数(Employee)

3.单个引用参数(Map)参数较多时使用

4.多个简单参数(Integer、Double、String) @Param()注解

5.多个引用参数(Employee,Dept)

五、数据输出 (resultType)

1.基本数据类型

2.实体类型(pojo)

3.List类型

4.Map类型、List类型

5.返回自增主键

六、数据库表字段和实体类属性对应关系

1.自动映射、手动映射 (起别名 alias)

2.手动映射(自动识别驼峰式命名规则)

3.手动映射ResultMap


一、MyBatis单表开发 - Mapper代理接口方式 (@Before、@After)

MyBatis中提供了名为 Mapper代理(或称为接口绑定)的操作方式。在实际开发中也使用该方式。

Mybatis中的Mapper接口相当于以前的Dao。但是区别在于,Mapper仅仅是接口,我们不需要提供实现类。

好处:可以提供多个参数,自定义返回值类型,利于后期扩展维护,符合JDBC开发习惯。

1、定义接口 相当于使用JDBC时的DAO接口,但是不需要写实现类

public interface EmployeeMapper {

    List findAll();

    Employee findById(Integer empId);

    int insertEmp(Employee emp);

    int updateEmp(Employee emp);

    int deleteEmp(Integer empId);

    //可以指定查询参数
    List findEmp(String ename,Double minSalary);
}

2、映射文件 (注意命名空间,为接口的全类名)






    
    
        SELECT emp_id empId,emp_name empName,emp_salary empSalary
        FROM t_emp
        WHERe emp_id = #{empId}
    
    
        INSERT INTO t_emp(emp_name,emp_salary)
        VALUES (#{empName},#{empSalary})
    
    
        DELETE FROM t_emp WHERe emp_id = #{empId}
    
    
        UPDATE t_emp SET emp_name= #{empName},emp_salary = #{empSalary}
        WHERe emp_id =  #{empId}
    

3、测试

public class TestMapperCRUD {
    SqlSession sqlSession;
    //所有方法执行前会先执行Before
    @Before
    public void before() throws IOException {
        //读取配置文件,创建SqlSessionFactory,获取sqlSession
        InputStream is = Resources.getResourceAsStream("mybatis-config.xml");
        SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(is);
        sqlSession = factory.openSession();

    }
    //所有方法执行后会执行After
    @After
    public void after(){
        //提交事务
        sqlSession.commit();
        //关闭资源
        sqlSession.close();
    }
    @Test
    public void findAll(){
        //获取一个Mapper对象
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        List empList = mapper.findAll();

        empList.forEach(emp -> System.out.println(emp));
    }
    @Test
    public void findById(){
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        Employee result = mapper.findById(1);
        System.out.println(result);
    }
    @Test
    public void insertEmp(){
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        int result = mapper.insertEmp(new Employee(null, "古力娜扎", 888.0));
        System.out.println(result);
    }
    @Test
    public void updateEmp(){
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        int result = mapper.updateEmp(new Employee(1, "小白", 130.0));
        System.out.println(result);
    }
    @Test
    public void deleteEmp(){
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        int result = mapper.deleteEmp(11);
        System.out.println(result);
    }
}

底层使用了动态代理来创建接口的实现类:

二、给SQL语句传参的两种方式 #{}  ${} 、模糊查询(Like)

结论:只要能用#{}肯定不用${},避免SQL注入。

1、#{}  底层使用PreparedStatement。安全,速度快,避免了注入、字符串拼接。

    
        SELECT emp_id empId,emp_name empName,emp_salary empSalary
        FROM t_emp
        WHERe emp_id = ${empId}
    
    @Test
    public void findById2(){
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        Employee result = mapper.findById2(2);
        System.out.println(result);
    }

使用 #{} ${} 实现模糊查询

#{}  推荐

    
        SELECT emp_id empId,emp_name empName,emp_salary empSalary
        FROM t_emp
        WHERe emp_name LIKE '%${ename}%'
    

三、给实体类起别名,方便resultType使用

方法1:给每一个类起别名,别名任意 (不推荐)

mybatis-config.xml

    
    

方法2:给一个包下的所有类起别名,别名为类名的首字母小写,其他字母不变 (推荐使用)

mybatis-config.xml

    

别名不区分大小写;别名任意,一般取类名;

注意:标签声明位置,要在之后

标签顺序 逗号","表示有顺序"|"表示子元素没有顺序要求

mybatis-3-config.tdt 源码 有顺序:
映射文件mybatis-3-mapper.dtd  源码 无顺序

四、数据输入

1.单个简单参数(Integer、Double、String)

#{} 中名称任意,建议和形参相同

//一个简单类型的参数 基本数据类型、包装类、String类
    public Employee findById(Integer empId);
    public List findEmp(String empName);
//简单参数
    @Test
    public void testFindById(){
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        Employee emp = mapper.findById(1);
        System.out.println(emp);
    }
    @Test
    public void testFindEmp(){
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        List emps = mapper.findEmp("李四");
        emps.forEach(emp-> System.out.println(emp));
    }

2.单个引用参数(Employee)

底层调用的是getter方法,如果没有getter方法,可以直接找同名属性

    //一个引用类型的参数
    public int insertEmp(Employee emp);
    
    
        INSERT INTO t_emp VALUES (null,#{empName},#{empSalary})
    

3.单个引用参数(Map)参数较多时使用

参数是map,#{},中需要与 map的 key对应。

    public List findEmp2(Map map);
    
        SELECT emp_id empId,emp_name empName,emp_salary empSalary
        FROM t_emp
        WHERe emp_name LIKE "%"#{param1}"%" AND emp_salary >= #{param2}
    
    
        SELECT COUNT(*)
        FROM t_emp
    
    @Test
    public void testSelectEmpCount(){
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        int n = mapper.selectEmpCount();
        System.out.println("共有记录: " + n + "条");
    }

2.实体类型(pojo)

可以写类的完整路径,也可以写别名

    Employee findById(Integer empId);
    
        SELECT emp_id empId,emp_name empName,emp_salary empSalary
        FROM t_emp
    
    @Test
    public void testFindAll(){
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        List empList = mapper.findAll();
        empList.forEach(employee -> System.out.println(employee));
    }

4.Map类型、List类型

当没有对应的实体类,如多表查询时使用。MAP相当于一个 key value对象,Sql 语句中别名就是key。

单条记录时:Map

    Map selectEmpNameAndMaxSalary();
    
    
        SELECT emp_id empId,emp_name empName,emp_salary empSalary
        FROM t_emp
    
    public void testFindAll2(){
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        List> list = mapper.findAll2();
        for (Map map : list) {
            System.out.println(map);
        }
    }

5.返回自增主键

添加参数:useGeneratedKeys="true"   keyProperty="empId"

返回自增主键,封装到实体类属性 empId 中。

    //添加员工,返回自增的员工编号(主键)
    public int insertEmpGeneratedKey(Employee emp);
    
    
        INSERT INTO t_emp VALUES (null,#{empName},#{empSalary})
    
    @Test
    public void insertEmpGeneratedKey() {
        EmployeeMapper mapper = sqlSession.getMapper(EmployeeMapper.class);
        Employee emp = new Employee(null, "萌白", 1200.0);
        int n = mapper.insertEmpGeneratedKey(emp);
        System.out.println("添加了几条记录:" + n);
        System.out.println("当前自增主键:" + emp.getEmpId());
    }

 注:Orecle 需要别的方式获取主键 (调用序列的值,Orecle不支持自增)。

六、数据库表字段和实体类属性对应关系

1.自动映射、手动映射 (起别名 alias)

如果数据库字段和实体类的属性一致,会自动映射到同名的成员变量。
否则需要起别名,没有映射成功属性值会为null。

    //表字段名与实体类属性名不对应,需要起别名
    
        SELECT * FROM t_emp
    

3.手动映射ResultMap

多表查询时一般都会使用
单表查询时,不满足驼峰命名,使用ResultMap,只映射一次,也有好处

    
    
    
        
        
        
        
    

字段不区分大小写,成员变量区分大小写.

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/926501.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号