| |
|
开发:
C++知识库
Java知识库
JavaScript
Python
PHP知识库
人工智能
区块链
大数据
移动开发
嵌入式
开发工具
数据结构与算法
开发测试
游戏开发
网络协议
系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程 数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁 |
-> Java知识库 -> mybatis中经典的设计模式 -> 正文阅读 |
|
[Java知识库]mybatis中经典的设计模式 |
? ? ? ? 我们知道有23个设计模式,但是大多停留在概念层面,真实开发中很少遇到。但是优秀的开源框架中使用了大量的设计模式,阅读源码并观察设计模式在其中的应用,能够更深入的理解设计模式。Mybatis源码中就是使用了大量的设计模式,正好是我们学习设计模式的沃土。 Mybatis至少遇到了以下的设计模式的使用: 1、Builder模式,例如SqlSessionFactoryBuilder、XMLConfigBuilder、XMLMapperBuilder、XMLStatementBuilder、CacheBuilder; 2、工厂模式,例如SqlSessionFactory、ObjectFactory、MapperProxyFactory; 3、单例模式,例如ErrorContext和LogFactory; 4、代理模式,Mybatis实现的核心,比如MapperProxy、ConnectionLogger,用的jdk的动态代理;还有executor.loader包使用了cglib或者javassist达到延迟加载的效果; 5、组合模式,例如SqlNode和各个子类ChooseSqlNode等; 6、模板方法模式,例如BaseExecutor和SimpleExecutor,还有BaseTypeHandler和所有的子类例如IntegerTypeHandler; 7、适配器模式,例如Log的Mybatis接口和它对jdbc、log4j等各种日志框架的适配实现; 8、装饰者模式,例如Cache包中的cache.decorators子包中等各个装饰者的实现; 9、迭代器模式,例如迭代器模式PropertyTokenizer; 接下来挨个模式进行解读,先介绍模式自身的知识,然后解读在Mybatis中怎样应用了该模式。 Builder模式 定义:将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。 光看这句话可能不好理解,举个例子比如说相同的注册流程可以注册出不同的公司(阿里,百度,腾讯等等),不同的注册信息可以表示出不同的公司。这样你应该就好理解一点了 如下图是SqlSessionFactoryBuilder类的结构图 由图可以看出SqlSessionFactoryBuilder定义了很多build方法,根据传入不同的参数构造SqlSessionFactory对象。 工厂模式 定义:定义一个创建对象的接口,让其子类自己决定实例化哪一个工厂类,工厂模式使其创建过程延迟到子类进行 如下图是SqlSessionFactory类结构图 SqlSessionFactory有两个实现类,SqlSessionFactory是简单工厂模式,用来创建SqlSession. 默认实现类中,可以分析SqlSession对象的创建过程 单例模式 单例模式(Singleton Pattern)是 Java 中最简单的设计模式之一。这种类型的设计模式属于创建型模式,它提供了一种创建对象的最佳方式。 这种模式涉及到一个单一的类,该类负责创建自己的对象,同时确保只有单个对象被创建。这个类提供了一种访问其唯一的对象的方式,可以直接访问,不需要实例化该类的对象。 注意:
ErrorContext私有化构造方法,实例通过ThreadLocal对象中获取,ThreadLocal是线程私有的,所以ErrorContext是线程安全的。 代理模式 定义:代理模式(Proxy)是通过代理对象访问目标对象,这样可以在目标对象基础上增强额外的功能 刚开始工作的几年大家都是依葫芦画瓢,并不会在意功能为什么这么做,使用mybatis的时候都没问为什么只定义了mapper接口没有实现类就可以使用mapper的方法?带着问题我们来分析一下mybatis的实现原理。 如下是获取mapper的代码 SqlSession sqlSession = sqlSessionFactory.openSession(); 我们在DefaultSqlSession类中看到 这里什么都没有做,跟到Configuration类中 接着跟到MapperRegistry中 继续查看 mapperProxyFactory.newInstance() 内部实现 到这里可以看到,实际返回了一个MapperProxy实例。 该MapperProxy类实现了InvocationHandler接口,并且实现了该接口的invoke方法。 通过这种方式,我们只需要编写Mapper.java接口类,当真正执行一个Mapper接口的时候,就会转发给MapperProxy.invoke方法 组合模式 组合(Composite Pattern)模式的定义:有时又叫作整体-部分(Part-Whole)模式,它是一种将对象组合成树状的层次结构的模式,用来表示“整体-部分”的关系,使用户对单个对象和组合对象具有一致的访问性,属于结构型设计模式。 mybatis中动态SQL的实现就是用组合模式, 模板方法模式 模板方法(Template Method)模式的定义如下:定义一个操作中的算法骨架,而将算法的一些步骤延迟到子类中,使得子类可以不改变该算法结构的情况下重定义该算法的某些特定步骤。 mybatis中sqlSession执行sql是通过Excutor,其中BaseExecutor使用的模板方法模式 BaseExecutor中定义了doQuery方法,具体实现在子类中完成。 适配器模式 定义:适配器模式(Adapter)的定义如下:将一个类的接口转换成客户希望的另外一个接口,使得原本由于接口不兼容而不能一起工作的那些类能一起工作。 说到适配器模式,看一下logging包中是实现, 由于各个厂商提供的日志api,日志级别等都不尽相同,所以mybatis对所有支持的日志框架做了封装,自定义了日志打印级别 ?error (错误) > warn (警告) > debug(调试信息)>trace mybatis 里定了了统一的日志接口,Log接口并定义了一系列的接口 日志集成核心类?org.apache.ibatis.logging.LogFactory tryImplementation方法里会先判断是否已经加载了日志组件,如果已经加载了则不会继续处理;并且这个方法做了异常的忽略,如果没有对应的日志组件也不会影响下一个组件的加载流程。 可以看出mybatis内部支持的优先级是:SLF4J | LOG4J | LOG4J2 | JDK_LOGGING | COMMONS_LOGGING | STDOUT_LOGGING | NO_LOGGING 装饰者模式 装饰器(Decorator)模式的定义:指在不改变现有对象结构的情况下,动态地给该对象增加一些职责(即增加其额外功能)的模式,它属于对象结构型模式。 在mybatis中,缓存的功能由根接口Cache(org.apache.ibatis.cache.Cache)定义。整个体系采用装饰器设计模式 迭代器模式 迭代器(Iterator)模式的定义:提供一个对象来顺序访问聚合对象中的一系列数据,而不暴露聚合对象的内部表示。迭代器模式是一种对象行为型模式 mybatis中PropertyTokenizer类的设计使用了迭代器模式,实现了java的Iterator接口 至此,全文完结了,有兴趣的可以去翻阅mybatis源码对照学习,吸取源码的优秀设计模式,在日常工作中写出优美的代码。 |
|
|
上一篇文章 下一篇文章 查看所有文章 |
|
开发:
C++知识库
Java知识库
JavaScript
Python
PHP知识库
人工智能
区块链
大数据
移动开发
嵌入式
开发工具
数据结构与算法
开发测试
游戏开发
网络协议
系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程 数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁 |
360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 | -2024/11/17 20:35:55- |
|
网站联系: qq:121756557 email:121756557@qq.com IT数码 |