在MyCat的源码中,很多对象都使用到了单例模式。

首先是MycatServer类,该实例必须全局唯一,所以这里涉及到JAVA的单实例模式,就是一个类只有唯一一个实例对象存在。先来看看mycat源码是怎么做的:

public class MycatServer {
private static final MycatServer INSTANCE = new MycatServer(); public static final MycatServer getInstance() {
return INSTANCE;
} private MycatServer() {
......
}
}
public final class MycatStartup {

    public static void main(String[] args) {
MycatServer server = MycatServer.getInstance();
} }

首先,将构造方法定义成私有的,这样外界不能再实例化该类。然后,提供一个公有的静态方法,使外界只能通过该方法来获取类实例,该方法返回一个类型为类本身的静态属性值,该属性值在类加载时调用私有构造方法初始化。这就保障了,该类只有唯一一个实例对象的存在。

上面这种写法是单实例创建的饿汉模式,线程安全,但浪费内存空间,不过mycat要运行MycatServer类是肯定要装载的,所以源码里这样用也没有问题。

还有一种静态内部类单例实现方式,集所有优点于一身,推荐使用:

public class Singleton {
private Singleton(){ }
private static class SingletonHolder{
private final static Singleton instance=new Singleton();
}
public static Singleton getInstance(){
return SingletonHolder.instance;
}
}

内部类不会随主类加载而加载,只有在第一次使用时才会加载,而单实例又是内部类的静态实例,所以用这种方式获取单实例,即是lazy loading,节省内存,又是线程安全且不需要同步锁的。所以用这种方式获取单实例最好。

参考文章:https://blog.csdn.net/john_chang11/article/details/78679867

另外,在Mycat的源码中有很多地方都使用到了饿汉式的单例模式,比如ZkConfig:

public class ZkConfig {
private ZkConfig() {
} private static ZkConfig ZKCFGINSTANCE = new ZkConfig(); public static ZkConfig getInstance() {
return ZKCFGINSTANCE;
} public void initZk(){
//...
}
}
public final class MycatStartup {
public static void main(String[] args) {
//use zk ?
ZkConfig.getInstance().initZk();
}
}

还有下面几个类:

public class TableStatAnalyzer implements QueryResultListener {
private final static TableStatAnalyzer instance = new TableStatAnalyzer(); private TableStatAnalyzer() {} public static TableStatAnalyzer getInstance() {
return instance;
}
}
public class QueryConditionAnalyzer implements QueryResultListener {
private final static QueryConditionAnalyzer instance = new QueryConditionAnalyzer(); private QueryConditionAnalyzer() {} public static QueryConditionAnalyzer getInstance() {
return instance;
}
}

还有一个使用静态内部类实现单例的:

public class MyCATSequnceProcessor {

    private static class InnerMyCATSequnceProcessor{
private static MyCATSequnceProcessor INSTANCE = new MyCATSequnceProcessor();
} public static MyCATSequnceProcessor getInstance(){
return InnerMyCATSequnceProcessor.INSTANCE;
}
}

Mycat源码中的单例模式的更多相关文章

  1. ASP.NET MVC Filters 4种默认过滤器的使用【附示例】 数据库常见死锁原因及处理 .NET源码中的链表 多线程下C#如何保证线程安全? .net实现支付宝在线支付 彻头彻尾理解单例模式与多线程 App.Config详解及读写操作 判断客户端是iOS还是Android,判断是不是在微信浏览器打开

    ASP.NET MVC Filters 4种默认过滤器的使用[附示例]   过滤器(Filters)的出现使得我们可以在ASP.NET MVC程序里更好的控制浏览器请求过来的URL,不是每个请求都会响 ...

  2. MyCat源码分析系列之——结果合并

    更多MyCat源码分析,请戳MyCat源码分析系列 结果合并 在SQL下发流程和前后端验证流程中介绍过,通过用户验证的后端连接绑定的NIOHandler是MySQLConnectionHandler实 ...

  3. MyCat源码分析系列之——SQL下发

    更多MyCat源码分析,请戳MyCat源码分析系列 SQL下发 SQL下发指的是MyCat将解析并改造完成的SQL语句依次发送至相应的MySQL节点(datanode)的过程,该执行过程由NonBlo ...

  4. MyCat源码分析系列之——BufferPool与缓存机制

    更多MyCat源码分析,请戳MyCat源码分析系列 BufferPool MyCat的缓冲区采用的是java.nio.ByteBuffer,由BufferPool类统一管理,相关的设置在SystemC ...

  5. MyCat源码分析系列之——前后端验证

    更多MyCat源码分析,请戳MyCat源码分析系列 MyCat前端验证 MyCat的前端验证指的是应用连接MyCat时进行的用户验证过程,如使用MySQL客户端时,$ mysql -uroot -pr ...

  6. MyCat源码分析系列之——配置信息和启动流程

    更多MyCat源码分析,请戳MyCat源码分析系列 MyCat配置信息 除了一些默认的配置参数,大多数的MyCat配置信息是通过读取若干.xml/.properties文件获取的,主要包括: 1)se ...

  7. 开源分布式数据库中间件MyCat源码分析系列

    MyCat是当下很火的开源分布式数据库中间件,特意花费了一些精力研究其实现方式与内部机制,在此针对某些较为重要的源码进行粗浅的分析,希望与感兴趣的朋友交流探讨. 本源码分析系列主要针对代码实现,配置. ...

  8. Android 源码中的设计模式

    最近看了一些android的源码,发现设计模式无处不在啊!感觉有点乱,于是决定要把设计模式好好梳理一下,于是有了这篇文章. 面向对象的六大原则 单一职责原则 所谓职责是指类变化的原因.如果一个类有多于 ...

  9. [转]数据库中间件 MyCAT源码分析——跨库两表Join

    1. 概述 2. 主流程 3. ShareJoin 3.1 JoinParser 3.2 ShareJoin.processSQL(...) 3.3 BatchSQLJob 3.4 ShareDBJo ...

随机推荐

  1. 分布式系统缓存系列之guava cache

      guava是google的一个开源java框架,其github地址是 https://github.com/google/guava.guava工程包含了若干被Google的 Java项目广泛依赖 ...

  2. 对于pycharm和vscode下,从外部复制文本内容为python字符串内容是会自动加\u202a解决办法

    先来看下这个python3源代码,表面上看没有语法毛病,如果源代码字符串内容是手动复制过来的文本内容,在pycharm和vscode下始终提示: pywintypes.error: (2, 'Shel ...

  3. POJ 1384 Piggy-Bank【完全背包】+【恰好完全装满】(可达性DP)

    题目链接:https://vjudge.net/contest/217847#problem/A 题目大意:   现在有n种硬币,每种硬币有特定的重量cost[i] 克和它对应的价值val[i]. 每 ...

  4. 【Java】基本I/O的学习总结

    计算机I/O 理解IO先要知道计算机对数据的输入输出是怎么处理的,下面一张图可以大致理解: 可以看出所谓输入是外部数据向CPU输入,而输出是CPU将数据输出到我们可见的地方,例如文件.屏幕等.而计算机 ...

  5. Java中的访问权限控制

    Java提供了public, private, protected 三个访问权限修饰词,提供了以下四种访问权限控制机制: 1.包访问权限: 2.Public访问权限: 3.Private访问权限: 4 ...

  6. python 列表返回重复数据的下标

    class Solution(object): def searchRange(self, nums, target): """ :type nums: List[int ...

  7. 给Linux系统管理员准备的Nmap命令的29个实用范例

    map即网络映射器对Linux系统/网络管理员来说是一个开源且非常通用的工具.Nmap用于在远程机器上探测网络,执行安全扫描,网络审计和搜寻开放端口.它会扫描远程在线主机,该主机的操作系统,包过滤器和 ...

  8. angular中的ng-options 用法

    <!DOCTYPE html><html> <head> <meta charset="UTF-8"> <title>& ...

  9. adblock 下载地址

    addblock 的作用: 防止追踪.恶意域名,过滤横幅广告.弹窗广告以及视频广告.   用以支持网站的非侵入式广告将不会被屏蔽 下载地址:https://pan.baidu.com/share/li ...

  10. python RandomForest跑feature重要性

    其实呢,就是直接调用一个函数的事情... #coding=utf-8 from sklearn.tree import DecisionTreeClassifier from matplotlib.p ...