Mybatis基础
Mybatis基础环境的搭建
利用Maven导入Mybatis所需的jar包
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.5.5</version>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.21</version>
</dependency>
编写Mybatis核心配置文件
<?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文件 -->
<properties resource = "jdbc.properties"/>
<typeAliases>
<!--给单个类起别名 -->
<typeAlias type="" alias=""></typeAlias>
<!--批量起别名 别名就是类名-->
<package name=""/>
</typeAliases>
<!-- environments配置数据库运行环境 default指定默认环境名 -->
<environments default="development">
<!--指定当前环境名 -->
<environment id="development">
<!--指定事务管理类型是JDBC -->
<transactionManager type="JDBC"></transactionManager>
<!--指定当前数据库的连接池 -->
<dataSource type="POOLED">
<!--数据库配置的基本信息 -->
<property name="driver" value="${jdbc.driver}"/>
<property name="url" value="${jdbc.url}"/>
<property name="username" value="${jdbc.username}"/>
<property name="password" value="${jdbc.password}"/>
</dataSource>
</environment>
</environments>
<!-- 加载映射 -->
<mappers>
<!-- 引入映射文件 相对于类路径 -->
<mapper resource = "Mapper.xml"/>
<!-- 将某个类注册为映射器接口 此时对应的配置文件的包名和文件名必须和类的类名和包名一致-->
<mapper class=""/>
<!-- 将某个包下的类全部注册为映射器接口 此时对应的配置文件的包名必须和类的包名一致-->
<package name=""/>
</mappers>
</configuration>
propertis文件
jdbc.driver = com.mysql.cj.jdbc.Driver
jdbc.url = jdbc:mysql://localhost:3306/design?serverTimezone=UTC
jdbc.username = root
jdbc.password = xxxxxxx
编写Mybatis映射文件
<?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="">
<!-- id为resultMap标签的唯一标识, type为方法返回的实体类型-->
<resultMap id="" type="">
<!-- id标签用于封装主键 property表示实体类字段, column表示数据库中的字段-->
<id property="" column=""/>
<!-- result标签用于封装其他字段 -->
<result property="" column=""/>
</resultMap>
</mapper>
基于xml开发
编写对应的接口
package Test;
import java.util.List;
public interface Demo {
List<String> findName();
}
编写简单Mybatis映射文件
<?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">
<!--namespace对应类的全类名 -->
<mapper namespace="Test.Demo">
<!--id对应类的方法名 resultType代表返回值 parameterType代表参数值-->
<select id="findName" resultType="string">
<!--然后在对应的标签下编写对应的sql语句 -->
select name from student where sex = "女"
</select>
</mapper>
SQL语句参数的获取与返回值的封装
返回值的封装
resultType: 如果方法返回的实体类中的字段值与表查询出来的字段名字一致,则查询结果自动封装到实体类中。
resultMap: 如果实体类的属性名和表中字段名不一致,可以使用ResultMapp实现手动映射,将查询字段封装到实体类中去。可以用于复杂数据的封装
<!-- id为resultMap标签的唯一标识, type为方法返回的实体类型-->
<resultMap id="" type="">
<!-- id标签用于封装主键 property表示实体类字段, column表示数据库中的字段-->
<id property="" column=""/>
<!-- result标签用于封装其他字段 -->
<result property="" column=""/>
</resultMap>
SQL参数的获取
一个参数的获取
当传入参数的值为一个时,可以用paramType来接收。如果数据类型是基本数据类型或是String时,#{}中的值可以随写,${}中的值只能写value。
多个参数的获取
这时用paramType不能达到同时传入多个值的效果。这时需要用到1.#{arg0}和#{arg1}来区分或者使用2.@Param主键来区分3.直接使用POJO来传递多个参数(推荐) 占位符中的值为get方法名后面的字母且首字母小写。
#{}与${}的区别
#{}表示一个占位符可以自动进行java类型和jdbc类型的转换。可以有效防止sql注入
${}表示一个拼接sql串可以进行字符拼接,可能出现sql注入问题
多表查询
一对一查询 从订单的角度出发 查询每个订单对应的客户 订单对象中有一个用户属性
一对多查询 从用户的角度出发 查询每个客户对应的订单 一个用户对象有一个订单数组对象
多对多查询 角色和职业 只从一个角度出发即可 相当于两个一对多。因此在Mybatis中可以把多对多查询转化为一对多查询,只有sql语句的编写不同,其余和一对多是一样的。
注意
在mybatis中一对多会被看成一对一。因为从用户角度来看用户与订单是一对多的关系,但从订单的角度来看一个订单是属于一个用户的属于一对一的关系。
嵌套查询
嵌套查询就是将将连接查询进行拆分。
一对一:在association标签中分别加入column和select属性并分别赋值为传递的参数名和sql语句
一对多、多对多: 在collection标签中分别加入column和select属性并分别赋值为传递的参数名和sql语句
动态SQL
if
set
foreach
延迟加载
延迟加载(懒加载):就是在需要用到关联表的数据时才进行加载,不需要用到就不进行加载
优点: 先从单表查询,需要时再进行关联表进行查询,这样可以提高数据库的性能。
缺点: 因为只有需要数据时才进行查询,这样在大批量查询数据时,因为查询也需要时间,所以这样会造成用户等待时间变长,造成用户体验变差。
在一对多、多对多中通常采用延迟加载
在多对一(一对一)中通常采用立即加载
延迟加载是基于嵌套查询来实现的
局部延迟加载:修改association和collection标签中的fetchType属性,修改它的值来改变加载策略, lazy为延迟加载eager为立即加载。
全局延迟加载:
<settings>
<!--开启全局延迟加载 -->
<setting name="lazyLoadingEnabled" value="true"/>
</settings>
当调用当前对象的equals、clone、hashCode、toString时会触发关联对象的查询。
局部加载优先级高于全局加载
缓存
以及缓存
二级缓存
基于注解开发
注解其实就是将对应的标签替换为注解来进行开发。一般对于简单的sql语句进行注解开发比较方便。而对于复杂的sql语句的编写一般不采用注解的方式进行开发。