本文是关于mybatis缓存模块设计的读后感,关于缓存的思考,关于mybatis的缓存源码详细分析在另一篇文章:https://www.cnblogs.com/gmt-hao/p/12448896.html,欢迎大家指教。

一般我们用到缓存的时候,只知道他很快,很强,还能持久,但是为什么他可以做到这些呢,有人会说这是天赋,遗传的,是的,你想的没错,确实是大佬们在构造这些的时候,赋予他这些能力,那今天我们就来剖析一下,大佬们干了啥,区区缓存就能这么厉害。

去大厂面试的时候,面试官总会喜欢问为什么,一开始,完全搞不懂我就去拧个螺丝,你问我造火箭怎么造我咋知道,后来在工作中遇到各种各样的问题,解决不了的时候,看着身边大佬们一层层点进去看源码分析问题的时候,瞬间觉得这多牛逼啊,或许一开始有动力看源码,了解为什么就是因为这个了吧(能装逼)。说回今天的主题-缓存,缓存在百度上的解释就是访问速度比一般随机存取存储器(RAM)快的一种高速存储器,其实对于我们而言就是一个访问速度特别快的数据库,一般而言是一种key-value形式存储的,因为便于查找,无论是类似redis还是我们自己程序中的,其实都是一个道理,他查找快的最大秘诀还是直接在内存中操作,但是由于现在互联网发展太快,大厂的用户量太大了,所以我们已经不能满足于此,那么我们怎么样找到对应的缓存的位置,更加是需要考量的,我们不由得想想,如果是我,那么该如何去设计一个缓存呢,或许能答出来的就是基于内存放到一个map当中读写了吧,那么mybatis作为一个优秀的orm框架,他是怎么设计缓存的呢,没准我们看了之后能够收到一点启发。

mybatis的缓存分为一级和二级,他除了缓存具备的简单读写功能之外,还额外添加了阻塞、清空策略、序列化、日志等功能并让你可以做到任意组合,够豪横吧,那么豪横的能力是怎么做到的呢,我们给他添加功能很简单,但是让我们可以随意组合,好像蛮难的哈,其实我们想一想,在java编程思想当中提到过一个比继承更加推荐的就叫组合,他其实就是不直接继承父类,而是将其引入对象中,这样既可以松耦合而且也能使用父类的功能。知道了这些我们再来看一下mybatis的代码

可以看到这些都是附加的一些功能,我们进去看看他是如何添加功能的。

                               

可以看到,就是我们之前想到的组合,我们将对象传入,并新增一些功能,不就达到了目的吗,而将这个新增之后的作为原始对象,再使用同样的方式去添加新功能,就可以达到任意组合的方式去使用,而这种方式在设计模式中被称为装饰器模式(哈哈,设计模式好像也没那么难)。

说完附加功能和设计模式,我们再看看他的最基本的功能-读写,其实最重要的就是缓存如何命中,可以看到mybatis的缓存命中,最重要的一个点就是cachekey

   

上图是cachekey的四个重要的参数,重写的equals也是相当的复杂,我们明明几个字符串就可以解决的问题,为啥要设计这么复杂?这不是很消耗资源吗,做这些的目的到底是啥呢,我们相信mybatis搞这么复杂绝不是为了装逼。一般来说,map的key为字符串,而mybatis支持动态sql,因此缓存的key不能仅仅通过String来表示,所以使用cachekey来封装多个影响缓存的因素,而判断两个cachekey是否相同关键是比较两个对象的hash值是否一致。每次更新数据同时也会刷新cachekey的值。我们已经知道mybatis是如何命中缓存的,其基本数据结构还是map,其实在我们自己设计缓存的时候,map也完全足够用了,像redis中双端链表,压缩列表,集合,跳表等数据结构,一般来说除了特殊情况,我们确实是不需要用到,所以对于缓存设计,也需要考虑一些其它的因素。

大家可以看下,mybatis的缓存基础数据结构是hashmap,对于一级缓存来说,由于他的作用域是当前会话,因此不会在多线程之间进行操作,不会有线程安全的问题,但是,二级缓存是跨sqlSession的,多线程并发的情况下,hashMap是肯定无法保证线程安全,所以,mybatis在设计的时候,二级缓存会加上一个synchronized装饰器,其实现就是在方法上面加synchronized关键字,他还有其他的一些装饰器比如LRU,FIFO等处理对象达到上限的清除策略,对于缓存的持久化,也是一个比较重要的话题,mybatis不像redis,他是本地缓存,随程序启动而启动,因此,没有做缓存持久化操作,但是,我们在设计缓存的时候,确实也需要考虑到这一点是否需要。

缓存的设计确实学问很大,本人才疏学浅,只能简单聊聊自己对于这方面的理解,看了mybatis的源码,才知道设计模式为啥这么被推崇,希望以后自己能走得更远吧!!!

mybatis缓存源码分析之浅谈缓存设计的更多相关文章

  1. Spring源码分析 之浅谈设计模式

    一直想专门写个Spring源码的博客,工作了,可以全身性的投入到互联网行业中.虽然加班很严重,但是依然很开心.趁着凌晨有时间,总结总结. 首先spring,相信大家都很熟悉了. 1.轻量级  零配置, ...

  2. 【JDK源码分析】浅谈HashMap的原理

    这篇文章给出了这样的一道面试题: 在 HashMap 中存放的一系列键值对,其中键为某个我们自定义的类型.放入 HashMap 后,我们在外部把某一个 key 的属性进行更改,然后我们再用这个 key ...

  3. netty源码分析 - Recycler 对象池的设计

    目录 一.为什么需要对象池 二.使用姿势 2.1 同线程创建回收对象 2.2 异线程创建回收对象 三.数据结构 3.1 物理数据结构图 3.2 逻辑数据结构图(重要) 四.源码分析 4.2.同线程获取 ...

  4. Mybatis源码分析之Cache二级缓存原理 (五)

    一:Cache类的介绍 讲解缓存之前我们需要先了解一下Cache接口以及实现MyBatis定义了一个org.apache.ibatis.cache.Cache接口作为其Cache提供者的SPI(Ser ...

  5. mybatis源码分析之06二级缓存

    上一篇整合redis框架作为mybatis的二级缓存, 该篇从源码角度去分析mybatis是如何做到的. 通过上一篇文章知道,整合redis时需要在FemaleMapper.xml中添加如下配置 &l ...

  6. mybatis源码分析之05一级缓存

    首先需要明白,mybatis的一级缓存就是指SqlSession缓存,Map缓存! 通过前面的源码分析知道mybatis框架默认使用的是DefaultSqlSession,它是由DefaultSqlS ...

  7. MyBatis 3源码分析

    Mybatis3.2源码分析: 一.加载配置文件.     使用SAX解析配置文件.读取xml配置文件后,调用XMLConfigBuilder.parse()方法,在parse方法中再调用parseC ...

  8. Mybaits 源码解析 (九)----- 全网最详细,没有之一:一级缓存和二级缓存源码分析

    像Mybatis.Hibernate这样的ORM框架,封装了JDBC的大部分操作,极大的简化了我们对数据库的操作. 在实际项目中,我们发现在一个事务中查询同样的语句两次的时候,第二次没有进行数据库查询 ...

  9. 深度 Mybatis 3 源码分析(一)SqlSessionFactoryBuilder源码分析

    MyBatis消除了几乎所有的JDBC代码和参数的手工设置以及对结果集的检索封装.MyBatis可以使用简单的XML或注解用于配置和原始映射,将接口和Java的POJO(Plain Old Java ...

随机推荐

  1. js中Tabs插件打开的标签页过多自动关闭

    js方法 function addTab(ResourceID, ResourceName, Url) { if (Url != "" && Url != null ...

  2. Guns自动化生成代码使用

    一.Guns简介 Guns基于Spring Boot2,致力于做更简洁的后台管理系统.包含系统管理,代码生成,多数据库适配,SSO单点登录,工作流,短信,邮件发送,OAuth2登录,任务调度,持续集成 ...

  3. RocketMQ(十):数据存储模型设计与实现

    消息中间件,说是一个通信组件也没有错,因为它的本职工作是做消息的传递.然而要做到高效的消息传递,很重要的一点是数据结构,数据结构设计的好坏,一定程度上决定了该消息组件的性能以及能力上限. 1. 消息中 ...

  4. spring boot 集成 Apache CXF 调用 .NET 服务端 WebService

    1. pom.xml加入 cxf 的依赖 <dependency> <groupId>org.apache.cxf</groupId> <artifactId ...

  5. android stdio 打包

    1.Build -> Generate Signed APK...,打开如下窗口 2.假设这里没有打过apk包,点击Create new,窗口如下 这里只要输入几个必要项 Key store p ...

  6. Head First 设计模式 —— 05. 单例模式

    全局变量的缺点 如果将对象赋值给一个全局变量,那么必须在程序一开始就创建好对象 P170 和 JVM 实现有关,有些 JVM 的实现是:在用到的时候才创建对象 思考题 Choc-O-Holic 公司使 ...

  7. Asp.Net Core 应用配置

    五种读取方式 五种读取方式依赖于 IConfiguration 和 IConfigurationRoot 对象 一.初级写法 //不区分大小写 string connectionString = _c ...

  8. transmission protocol

    传输层主要定义了主机应用程序间端到端的连通性,它一般包含四项基本功能 . 将应用层发往网络层的数据分段或将网络层发往应用层的数据段合并 建立端到端的链接,主要是建立逻辑连接以传送数据流 将数据段从一台 ...

  9. 【JavaWeb】现代 JavaScript 教程

    js_model_tutorial !!待更新 前言 现代 JavaScript 教程的学习笔记,它是一份不错的学习资源,感谢开源. 中文链接 基础 函数 代码示例 函数的声明方式 function ...

  10. 对微信小程序的生命周期进行扩展 – Typescript 篇

    最近利用业余时间倒腾了一个微信小程序,主要目的是横向比较一些业界小程序平台的架构和做法.因为有在其他平台长期的开发经验,对于小程序的一些机制做了一些辩证的思考.例如,小程序的页面,其实不是一个页面,而 ...