一文彻底搞懂Mybatis系列(七)之使用Mybatis的小技巧

本文涉及的产品
RDS MySQL Serverless 基础系列,0.5-2RCU 50GB
云数据库 RDS PostgreSQL,高可用系列 2核4GB
云数据库 RDS MySQL,高可用系列 2核4GB
简介: 一文彻底搞懂Mybatis系列(七)之使用Mybatis的小技巧

一、#{}和${}的区别

1、演示代码

(1)准备实体类 Account

package com.powernode.bank.pojo;
public class Account {
    private Long id ;
    private String actno;
    private Double balance;
    ....

(2)准备 AccountMapper.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="account">
    <select id="selectByActno" resultType="com.powernode.bank.pojo.Account">
        select * from t_act where actno = #{actno}
    </select>
</mapper>

(3)测试类

public class Test {
    @org.junit.Test
    public void test1(){
        SqlSession sqlSession = SqlSessionUtil.openSqlSession();
        Account account = sqlSession.selectOne("account.selectByActno", "act001");
        System.out.println(account.toString());
    }
}
先测试  #{} 语法,运行结果如下:
17:03:22.973 default [main] DEBUG o.a.i.t.jdbc.JdbcTransaction - Setting autocommit to false on JDBC Connection [com.mysql.cj.jdbc.ConnectionImpl@71ba6d4e]
17:03:22.978 default [main] DEBUG account.selectByActno - ==>  Preparing: select * from t_act where actno = ?
17:03:23.026 default [main] DEBUG account.selectByActno - ==> Parameters: act001(String)
17:03:23.080 default [main] DEBUG account.selectByActno - <==      Total: 1
Account{id=1, actno='act001', balance=10004.0}
在测试 ${}语法,运行结果如下:
17:04:15.335 default [main] DEBUG o.a.i.t.jdbc.JdbcTransaction - Setting autocommit to false on JDBC Connection [com.mysql.cj.jdbc.ConnectionImpl@1cf6d1be]
17:04:15.342 default [main] DEBUG account.selectByActno - ==>  Preparing: select * from t_act where actno = act001
17:04:15.414 default [main] DEBUG account.selectByActno - ==> Parameters: 
org.apache.ibatis.exceptions.PersistenceException: 
### Error querying database.  Cause: java.sql.SQLSyntaxErrorException: Unknown column 'act001' in 'where clause'

2、区别描述

1、#{}:底层使用PreparedStatement。特点:先进行SQL语句的编译,
然后给SQL语句的占位符问号?传值。可以避免SQL注入的风险。
2、${}:底层使用Statement。特点:先进行SQL语句的拼接,
然后再对SQL语句进行编译。存在SQL注入的风险。优先使用#{},这是原则。
避免SQL注入的风险。

二、什么时候使用 ${}

1、当需要往sql语句中,传入关键字时,可以是使用${},比如 前端传递排序字段值 asc或者 desc

案例场景:前台传入排序字段值,该值为mysql关键字,我们分别使用#{}和${}来处理:

#{}的执行结果,将关键字加了单引号 ,造成语法错误:
select car_num as carNum, brandfrom t car order by produce_time 'asc'
${}的执行结果,相当于拼接了关键字:
select car_num as carNum, brandfrom t car order by produce_time asc
2、或者想先进行sql语句拼接,然后再对sql语句进行编译,再执行时,也可以使用 ${} 

三、拼接表名

场景:
现实业务当中,可能会存在分表存储数据的情况。因为一张表存的话,数据量太大。查询效率比较低。可以将这些数据有规律的分表存储,这样在查询的时候效率就比较高。因为扫描的数据量变少了。
日志表:专门存储日志信息的。如果t_log只有一张表,这张表中每一天都会产生很多log,慢慢的,这个表中数据会很多。
怎么解决问题?
可以每天生成一个新表。每张表以当天日期作为名称,例如:
t_log_20220901 t_log_20220902
....
你想知道某一天的日志信息怎么办?
假设今天是20220901,那么直接查:t_log_20220901的表即可。
所以 ,向SQL语句当中拼接表名,就需要使用${}

四、批量删除

1、批量删除:一次删除多条记录。
2、批量删除的SQL语句有两种写法:
第一种or: delete from t car where id=1 or id=2 or id=3
第二种int: delete from t car where id in(1,2,3);
应该采用 ${} 的方式:
delete from t_car where id in(${ids});
代码如下:
<?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="account">
    <delete id="deleteBatch">
        delete from t_act where id in (${ids})
    </delete>
</mapper>
@Test
    public void testDelete(){
        SqlSession sqlSession = SqlSessionUtil.openSqlSession();
        int deleteBatch = sqlSession.delete("deleteBatch", "1,2");
        System.out.println(deleteBatch);
        sqlSession.commit();
        sqlSession.close();
    }
运行结果
22:20:06.304 default [main] DEBUG account.deleteBatch - ==>  Preparing: delete from t_act where id in (1,2)
22:20:06.376 default [main] DEBUG account.deleteBatch - ==> Parameters: 
22:20:06.380 default [main] DEBUG account.deleteBatch - <==    Updates: 2
2

五、模糊查询

模糊查询: like

需求:根据汽车品牌进行模糊查询
select * from t car where brand like'%奔驰%'; 
select * from t car where brand like'%比亚迪%';
在mybatis的xml文件中有如下写法:
第一种方案:  '%${brand}%'
第二种方案:concat函数,这个是mysql数据库当中的一个函数,专门进行字符串拼接
concat('%' ,#{brand},'%')
第三种方案:比较鸡肋了。可以不算。
concat('%','${brand}', '%')
第四种方案:    "%"#{brand} "%"

六、起别名

1、核心配置文件mybatis-config.xml 增加typeAliases标签,用来配置别名
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
        PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
    <properties resource="jdbc.properties"/>
    <typeAliases>
        <typeAlias type="com.powernode.bank.pojo.Account" alias="account"/>
    </typeAliases>
    <environments default="development">
    .......
2、修改sql文件,resultType的值可以直接使用别名,并且不区分大小写
<select id="selectActLike" resultType="account">
          select * from t_act where actno like concat ('',#{actno},'%')
    </select>

七、mybatis-config.xml文件的mapper配置

1、mybatis-config.xml文件中的mappers标签。

<mapper resource="CarMapper.xml"/> 要求类的根路径下必须有:CarMapper.xml
<mapper url="file:///d:/CarMapper.xml"/> 要求在d:/下有CarMapper.xml文件
<mapper class="全限定接口名,带有包名"/>

2、mapper标签的属性可以有三个:

resource:这种方式是从类的根路径下开始查找资源。采用这种方式的话,
你的配置文件需要放到类路径当中才行。
url:这种方式是一种绝对路径的方式,这种方式不要求配置文件必须放到类路径当中,
哪里都行,只要提供一个绝对路径就行。这种方式使用极少
 class:这个位置提供的是mapper接口的全限定接口名,必须带有包名的。

3、思考:mapper标签的作用是指定SalMapper.xml文件的路径,指定接口名有什么用呢?

<mapper class="com.powernode.mybatis.mapper.CarMapper"/>
如果你class指定是:com.powernode.mybatis.mapper.CarMapper
那么mybatis框架会自动去com/powernode/mybatis/mapper目录下查找CarMapper.xml文件。

注意:也就是说:

如果你采用这种方式,那么你必须保证CarMapper.xml文件和CarMapper接口必须在同一个目录下。
并且名字一致。 CarMapper接口-> CarMapper.xml LogMapper接口-> LogMapper.xml
....

八、获取插入数据时自动生成的主键

<insert id="insertAct" useGeneratedKeys="true" keyProperty="id">
        insert into t_act values (null,#{actno},#{balance})
    </ins

说明:

useGeneratedKeys="true"  使用自动生成的主键值
keyProperty="id"   指定主键值赋给对象的哪个属性


相关实践学习
每个IT人都想学的“Web应用上云经典架构”实战
本实验从Web应用上云这个最基本的、最普遍的需求出发,帮助IT从业者们通过“阿里云Web应用上云解决方案”,了解一个企业级Web应用上云的常见架构,了解如何构建一个高可用、可扩展的企业级应用架构。
MySQL数据库入门学习
本课程通过最流行的开源数据库MySQL带你了解数据库的世界。 &nbsp; 相关的阿里云产品:云数据库RDS MySQL 版 阿里云关系型数据库RDS(Relational Database Service)是一种稳定可靠、可弹性伸缩的在线数据库服务,提供容灾、备份、恢复、迁移等方面的全套解决方案,彻底解决数据库运维的烦恼。 了解产品详情:&nbsp;https://www.aliyun.com/product/rds/mysql&nbsp;
相关文章
|
Kubernetes 监控 云计算
Docker与云计算平台集成:AWS、Azure、GCP完全指南
Docker和云计算平台的结合,如AWS(Amazon Web Services)、Azure(Microsoft Azure)和GCP(Google Cloud Platform),为现代应用的构建和部署提供了巨大的便利性。本文将深入研究如何与这些主要云计算平台集成Docker,提供更多示例代码和详细指南,帮助大家更全面地利用这些强大的工具。
|
监控 中间件 Linux
深入Linux设备模型:开发者指南
Linux的设备模型是操作系统管理硬件设备的一种高级抽象,它不仅涉及到设备驱动程序的加载和卸载,还包括设备之间的关系、设备的状态管理以及与用户空间通信的机制。理解Linux的设备模型对于应用开发人员来说至关重要,它有助于开发出更加稳定、高效的应用程序。🌟
深入Linux设备模型:开发者指南
|
8月前
|
供应链 搜索推荐 API
深度解析1688 API对电商的影响与实战应用
在全球电子商务迅猛发展的背景下,1688作为知名的B2B电商平台,为中小企业提供商品批发、分销、供应链管理等一站式服务,并通过开放的API接口,为开发者和电商企业提供数据资源和功能支持。本文将深入解析1688 API的功能(如商品搜索、详情、订单管理等)、应用场景(如商品展示、搜索优化、交易管理和用户行为分析)、收益分析(如流量增长、销售提升、库存优化和成本降低)及实际案例,帮助电商从业者提升运营效率和商业收益。
428 20
|
数据采集 存储 数据可视化
数据清洗
数据清洗
447 2
|
存储 关系型数据库 MySQL
linux安装MySQL8.0,密码修改权限配置等常规操作详解
linux安装MySQL8.0,密码修改权限配置等常规操作详解
525 0
|
数据采集 机器学习/深度学习 存储
性能调优指南:针对 DataLoader 的高级配置与优化
【8月更文第29天】在深度学习项目中,数据加载和预处理通常是瓶颈之一,特别是在处理大规模数据集时。PyTorch 的 `DataLoader` 提供了丰富的功能来加速这一过程,但默认设置往往不能满足所有场景下的最优性能。本文将介绍如何对 `DataLoader` 进行高级配置和优化,以提高数据加载速度,从而加快整体训练流程。
1829 0
|
UED Python
python使用 requests 设置读取超时时间
python使用 requests 设置读取超时时间
609 0
|
Java Android开发
盒子电源管理相关
盒子电源管理相关
58 1
|
弹性计算 大数据 测试技术
阿里云轻量应用服务器2核2G3M和2核4G4M配置价格表
阿里云轻量应用服务器2核2G3M和2核4G4M配置价格表,2023年阿里云服务器5月优惠价格表来了,CPU内存配置可选2核2G、2核4G、2核8G、2核16G、4核4G、4核8G、4核16G、4核32G、8核8G、8核16G、8核32G、8核64G等配置,云服务器包括轻量应用服务器和云服务器ECS,ECS实例可选通用算力型u1、计算型c7、通用型g7和内存型r7实例
641 0
|
JavaScript 测试技术 vr&ar
动态规划之背包问题——背包三讲(01背包,完全背包,多重背包)(一)
动态规划之背包问题——背包三讲(01背包,完全背包,多重背包)(一)
270 0
动态规划之背包问题——背包三讲(01背包,完全背包,多重背包)(一)