Mybatis 个人理解笔记 [总]

Mybatis 笔记

  1. 什么是MyBatis ?
        MyBatis 是一款优秀的持久层框架,它支持自定义 SQL、存储过程以及高级映射。
        MyBatis 免除了几乎所有的 JDBC 代码以及设置参数和获取结果集的工作。
        MyBatis 可以通过简单的 XML 或注解来配置和映射原始类型、接口和 Java POJO(Plain Old Java Objects,普通老式 Java 对象)
                      为数据库中的记录。
  1. 搭建步骤 (配置文件的使用)
        i. 引入Mybatis坐标
        ii. 创建实体类,写dao层接口
        iii. 创建映射文件(也就是dao层接口的实现类)
        iv. 创建Mybatis配置文件
            iv.i. 配置mybatis的环境(数据源,事务机制类型,映射配置文件所在的位置)
        v. 测试
            v.i. 加载Mybatis配置文件
            v.ii. 创建工厂构造器对象(SqlSessionFactoryBuilder),读取配置文件
            v.iii. 构造工厂(SqlSessionFactory),通过工厂创建连接(SqlSession)
            v.iv. 通过反射加载接口的字节码(getMapper),动态生成接口的实现类,并调用方法,释放资源
  1. 映射文件的标签属性说明
        <select> 标签:
                id 属性: 用于指定接口中的方法
        SelectKey 标签 只能写在Insert 标签中
                keyColumn 属性: 数据库表中的字段
                keyProperty 属性: 实体类中的属性
                resultType 属性: 返回时的属性
                SQL语句: select last_insert_id(); 查询最后新增加的id
                order 属性: AFTER 新增后执行查询id语句(默认值) BEFORE 先查找id再新增
        resultType 属性:  用于指定结果集的类型.
        resultMap 属性: 建立查询的列名和实体类的属性名称不一致时建立对应关系。从而实现封装。
                      还可以实现将查询结果映射为复杂类型的 pojo,比如在查询结果映射对象中包括 pojo 和 list 实现一对一查询和一对多查询。
        resultMap 标签:
                 id 属性: 给定一个唯一标识,是给查询 select 标签引用用的。
                 type 属性:指定实体类的全限定类名
                 resultMap里面的标签:
                                        id 标签: 用于指定主键字段
                                        result标签: 用于指定非主键字段
                                                这两个标签里面的属性:
                                                column 属性: 用于指定数据库列名
                                                property 属性: 用于指定实体类属性名称
        parameterType 属性:  此属性可写可不写
                     用于指定传入参数的类型.  
                     如果参数是一个对象那么需要写类的全限定类名
        SQL语句中的#{} 字符: 它代表占位符,相当于jdbc所学的,都是用于执行语句时替换成实际的数据. 具体的数据是由#{}里面的内容决定的.
                #{} 中内容的写法:
                      如果是基本类型可以随便写.(推荐传过来参数名是什么就写什么就好)
                      如果是一个对象那么需要采用ognl表达式#{对象.属性}     此种书写方法已过时,直接写传过来的属性名即可(必须)
        ognl 表达式:
            它是 apache 提供的一种表达式语言,全称是:
            Object Graphic Navigation Language 对象图导航语言
            它是按照一定的语法格式来获取数据的。
            语法格式就是使用 #{对象.属性}的方式
  1. 配置文件的标签属性说明
        configuration
            -properties(属性)
                    --property
            -settings(全局配置参数)
                    --setting
            -typeAliases(类型别名)
                    --typeAliase
                            alias 属性: 自定义别名
                            type 属性: 类的全限定类名
                    --package           (批量别名定义,扫描整个包下的类,别名为类名(首字母大写或小写都可以))
                            name 属性: 包路径.
            -typeHandlers(类型处理器)
            -objectFactory(对象工厂)
            -plugins(插件)
            -environments(环境集合属性对象)
                    --environment(环境子属性对象)
                            --transactionManager(事务管理)
                            --dataSource(数据源)
            --mappers(映射器)
                    --mapper
                            resource 属性: 指定映射文件
                            class 属性: 使用注解形式,指定需要实现那个接口增强那些方法
                    --package
                            name 属性: 注册指定包下的全部接口(也就是让Mybatis通过反射Proxy.newProxyInstance(被代理类的类加载器,被代理类的字节码文件,代理策略))
  1. 说说 #{} 和 ${}有什么区别
        #{} 是占位符的方式,在执行语句时会替换成实际的数据(是jdbc preparedStatement向占位符中设置值)
        ${} 是字符串拼接的方式, 可能会进行SQL注入 例如 select * from user -- where id = 1   SQL语句--后面都注释掉了
  1. Mybatis 的三种数据源
        i. UNPOOLED 不使用连接池的数据源
        ii. pooled 使用连接池的数据源
        iii.jndi 使用jndi实现的数据源
  1. Mybatis 中连接的获取分析
        当调用SqlSession.selectList() Mybatis底层会创建连接会操作数据库
  1. Mybatis 中事务的管理
          每次必须手动提交,因为从连接池中取出连接会connection.setAutoCommit(false)
  1. Mybatis 动态SQL语句
        <if>标签 : 从实体类中取值,使用不同的SQL语句查询.
             比如在 id 如果不为空时可以根据 id 查询,如果 username 不同空时还要加入用户名作为条件.这种多条件组合查询
            test 属性: 表示如何判断. 例如: "属性 != null and 属性 != ''" 表示该属性!=null 并且 != 空字符串 会执行if里面的语句 否则不执行
        <where>标签 : 如果where 标签里面的 if 标签里面的语句有一条可以执行,那么就会有where 语句 否则 没有where
                          例如: select * from user <where> <if test="name != null and name != ''"> name = #{name}</if> </where> 如果test为true
                            那么执行语句为 : select * from user where name = #{name} 否则 select * from user
        <set>标签 update <set> <if test="username != null and username != ''">username = #{username},</if> <if test="name != null and name != ''">name = #{name},</if></set>
                最后会自动去掉逗号
        <foreach>标签 : 相当于 for 循环,用于遍历集合,使用需求 批量添加,批量删除等等
            collection 属性: 代表要遍历的集合元素,直接参数名(属性名),注意编写是不要写#{}
            open 属性: 代表语句开始部分
            clone 属性: 代表结束部分
            item 属性: 代表遍历集合的每个元素,生成的遍历名
            sperator 属性: 代表分隔符
                select * from user where id in(xx,xx,xx,xx)
                例如: select * from user <where> <if test ="变量名 != null and 变量名.size() > 0">
                                <foreach collection ="变量名" open="id in(" clone=")" item="index" sperator=",">
                                        #{index}
                                </foreach>
                            </if></where>
        <sql>标签 : 主要用于抽取共性sql语句,进而达到高可用的目的,与之匹配的是<include>标签
            id 属性: 唯一标识符
        <include>标签 :
            refid 属性: 引用(指定)sql标签的唯一标识符
  1. Mybatis 的多表查询之一对一
        <result id="唯一标识符" type="类的全限定类名">
            <id column="列名" property="类属性名称"/>
            <result column="列名" property="类属性名称"/>
            <association property="类属性名" javaType="属性(另一个对象)的全限定类名(别名)">
                <id column="列名" property="(另一对象的)类属性名称"/>
                <result column="列名" property="(另一个对象的)类属性名称"/>
            </association>
        </result>
  1. Mybatis 的多表查询之一对多
        <result id="唯一标识符" type="类的全限定类名">
            <id column="列名" property="类属性名称"/>
            <result column="列名" property="类属性名称"/>
            <!-- collection标签 : 用于建立一对多中集合属性的对应关系
                        property 属性: 用于指定类中的属性名
                        javaType 属性: 用于指定是什么集合类型
                        ofType 属性: 用于指定集合中都是什么类型(泛型)
                        例如: List<Account> accounts
            -->
            <collection property="accounts" javaType="list" ofType="account">
                <id column="列名" property="(另一对象的)类属性名称"/>
                <result column="列名" property="(另一个对象的)类属性名称"/>
            </collection>
        </result>
  1. association 和 collection 有什么区别?
        association标签是用于建立一对一的映射关系
        collection标签是用于建立一对多的映射关系
  1. Mybatis 的多表查询之多对多
    其实就是两个一对多
    例如: 用户表 用户角色表 角色表
    用户相关信息 用户id,角色id 角色相关信息
    一个用户可以有多个角色,一个角色可以有多个用户使用
  2. Mybatis 的策略
            延迟加载策略(个人感觉用处不太大,如有想要了解的可以自行百度搜索)
一下为个人理解,如有不同理解可以留言评论,我会观看并和码友们一起交流
                简单介绍一下, 也就是当开启延迟加载策略时,是什么时候需要数据什么时候查询数据库.  也称之为'懒加载' 大大提高数据库性能
                    坏处: 如果需要查询大批量数据时,有可能会造成用户等待时间过长,造成用户体验下降.
                    也不是完全没用. 也可以像阿里 每次数据库表访问不能级联3张表 也可以开启延迟加载策略
            缓存策略
  1. Mybatis 的缓存(缓存策略)
        分为一级缓存 和 二级缓存
        一级缓存的范围: 只在一个SqlSession(也就是连接,一个连接缓存一次),连接不close和clearCache(清空本地缓存),一级缓存就一直存在,但是作用范围太小
                证实一级缓存: 只需要通过同一个SqlSession调用两次相同的方法,并且开启日志,查看是否发送了两次SQL语句
                问题: DML(增删改)操作时会清空一级缓存,这样做是为了解决脏读问题(也就是要保持缓存数据和数据库中的数据一致) 作用范围太小
        二级缓存的范围: 多个SqlSession共同操作同一个本地二级缓存区域(也就是JVM开辟的一块Map数据类型),二级缓存跨SqlSession的.
                开启二级缓存: 二级缓存配置文件中默认是开启的,但是不知道哪个映射文件需要缓存,需要在映射文件中添加<cache/>标签 开启二级缓存
                标记那些SQL语句开启二级缓存: 需要在<select>标签 上的userCache属性值设置为true 表示当前标签开启二级缓存  
                                     警告: 此处经过测试 <select>标签上面userCache属性值设置为true与不设置没有任何区别,只需要在映射文件中配置<cache/>标签即可.
                问题: 同上,最主要的是范围够了但是太占用jvm的运行内存空间
  1. 说说Mybatis 的缓存策略
        一级缓存默认开启,但是作用范围只在一个SqlSession,作用范围太小
        二级缓存 配置文件中默认开启,只需要在映射文件中添加<cache/>标签即可,但是它所采用的是jvm分配的map空间,如果项目缓存数据越来越多,太占用jvm资源,并且系统只分配固定的jvm空间
  1. Mybatis 注解式开发
        增删改
             @Insert("sql") @Delete("sql") @Update("sql") @Select("sql") CRUD
             @MapKey、@Options、@SelelctKey、@Param、@InsertProvider、@UpdateProvider、@DeleteProvider
            @SelectProvider: 实现动态 SQL 映射
        结果集映射
             @Result:实现结果集封装
             @Results:可以与@Result 一起使用,封装多个结果集
             @ResultMap:实现引用@Results 定义的封装
             @One:实现一对一结果集封装
             @Many:实现一对多结果集封装
             @ResultType、@ConstructorArgs、@Arg、@TypeDiscriminator、@Case
       缓存
             @CacheNamespace:实现注解二级缓存的使用
             @Property、@CacheNamespaceRef、@Flush
       基本上使用率不太,Mybatis 好不容易把持久层做到了解耦效果,如果@Select 配合@Result 和 @Results 封装结果集这不又耦合了么,这是其一
       其二: 如果是复杂对象映射关系呢? 还是推荐使用映射文件
   如果对Mybatis注解开发感兴趣可以访问 [Mybatis注解开发](http://www.tianshouzhi.com/api/tutorials/mybatis/393)
   Mybatis 面试题可以参考 [Mybatis相关面试题](https://blog.csdn.net/a745233700/article/details/80977133) 
   这两篇文章都挺不错的
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值