单例模式是我们日常工作中接触最多,也可以说是最简单的一个设计模式。那么什么是单例呢?为什么要用这种模式?
单例简单来说就是只进行一次初始化,以Imageloader为解释为什么要用这种模式,因为ImageLoader会涉及到大量的io和网络请求,消耗大量的资源,为了减少资源的消耗和浪费,便出现了单例模式。
我们常见的单例模式有很多种实现方式,比如饿汉模式、懒汉模式、双加锁模式等等,下面以简单的例子来一一记录这些单例模式的实现:
1、饿汉模式
为何称之为“饿汉模式”呢?因为饿汉经常会突然的饿意袭来,为了在饿意到来的时候,有足够的食物,饿汉需要提前将食物准备好。我们的“饿汉模式”也是这样,在使用之前便为我们初始化了单例对象,需要注意的是初始化的时候,还没有产生子线程,因此不会存在线程安全的问题。

public class Hungry {private static Hungry INSTANCE = new Hungry();private Hungry(){}public static Hungry getInstance(){return INSTANCE;}
}

2、懒汉模式
该模式是经常与饿汉一起提起的,为什么叫懒汉呢?是因为该模式下不会提前进行初始化,而是在需要的时候才会进行初始化。在这种模式下,需要注意的是高并发情况下,会出现线程安全问题,因此需要引入同步锁!

public class Lazy {private static Lazy INSTANCE = null;private Lazy(){}public static synchronized Lazy getInstance(){if(INSTANCE == null){INSTANCE = new Lazy();}return INSTANCE;}
}

“饿汉模式”与“懒汉模式”的区别在于初始化的时间不同,“饿汉模式”下无论是否会调用,都会进行初始化,造成资源的浪费,而“懒汉模式”只会在需要的时候初始化,不会造成资源浪费。
3、双加锁(DCL)模式
在“懒汉模式”,虽然不会每次调用getInstance都会进行初始化,但是每次调用都会使用同步锁,也会造成不必要的浪费,因此出现了“双加锁模式”,代码如下:

public class DoubleCheckLocked {private static DoubleCheckLocked INSTANCE;private DoubleCheckLocked(){}public static DoubleCheckLocked getInstance(){if(INSTANCE == null){synchronized (DoubleCheckLocked.class){if(INSTANCE == null){INSTANCE = new DoubleCheckLocked();}}}return INSTANCE;}
}

从上面的代码,我们可以看到两次判空操作,第一次判空是为了判断是否需要加锁,而第二次判断则是为了保证只会初始化一次。这么看来,这种模式是不是一种最优的方案呢?实际上是不支持这种写法的,因为会有一个叫做“重排序”的问题,重排序通常是编译器或运行时环境为了优化程序性能而采取的对指令进行重新排序执行的一种手段。
正常情况下,INSTANCE = new DoubleCheckLocked();这句代码可以分为三个步骤:
a.分配对象的内存空间
b.初始化对象
c.设置sInstance指向刚分配的内存地址
但是由于重排序的存在,在高并发的环境下,为了提高运行速率,可能会让bc的步骤发生变化,这样就有可能导致某个线程调用获取到了一个还未初始化的对象。
JDK1.5之后针对上面的问题,官方对volatile进行了优化,因此在1.6之后也可以通过volatile实现。
4、静态内部类实现单例

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

因为INSTANCE 的定义是private static final,因此只会在第一次调用的时候才会初始化,因此不会涉及线程安全问题。另外外部类加载的时候并不会进行初始化,因此不会占用内存。

当然除了上面四种方式,我们还可以通过枚举或者一些容器,如HashMap等实现单例,枚举无需解释,本身枚举就是为单例而生,而使用容器等可能会涉及到线程安全问题,在某些场景下使用需要思考清楚。
5、枚举实现单例

public class Enum {public  enum EnumEnum{ENUM;private EnumEnum(){INSTANCE = new Enum();}private  Enum INSTANCE;public  Enum getINSTANCE(){return INSTANCE;}}private Enum(){}public static Enum getInstance(){return EnumEnum.ENUM.getINSTANCE();}
}

6、容器实现单例

public class Container {private static Map<String,Container> SINGLEMAP = new HashMap<>();public static void putSingle(String key,Container value){if(!SINGLEMAP.containsKey(key)){SINGLEMAP.put(key,value);}}public  static  Container getInstance(String key){return SINGLEMAP.get(key);}
}

综上所述,实现单例的方法有很多种,其核心就是为了减少初始化的次数,从而减少资源的浪费,多用在涉及到IO、网络请求等场景。道路千万条,针对不同的场景,选择最合适的方案!

一人一猫旅行记之浅析单例模式相关推荐

  1. 小e的每日一画 之 飞毯旅行记 20071231

    作者:小e,年龄:5岁9个月,打字:老豆 飞毯旅行记 有一天,阿魔对阿豆说:"咱们家那么穷,能买什么呢?" 阿豆说:"我也不知道,咱们找一个聪明的人去问问吧." ...

  2. 兔年伊始谈闲书:三体-乌合之众-百年孤独 和《猫城记》(随笔)

     引言  " 各位读者,我们都兔年大吉,新春快乐. 我本想写一篇<公有云换帅转舵后的错误经验和正经歪念>,但刚过年就炮火味十足,觉得有失体面.所以就写了篇读书的散记杂记. 本文和 ...

  3. 读《猫城记》 | 人间失格

    猫城记是老舍先生在1932年完成的一部科幻讽刺小说,故事是老舍先生梦到自己乘坐飞船到火星,结识到当地一种智慧生物--猫人,进而了解到猫人的社会现状,失格的经济.教育.政治,直到猫人国灭亡,返回地球. ...

  4. 软件需求分析之猫咪记单词

    软件需求分析之猫咪记单词 一.软件设计目标 目前,所有学生都面临学习英语的问题.在大学生中学生对于手机的应用十分频繁,所以我们设置单词解屏,可以使学生拿起手机就学习英语,提高学习效率,应用零散时间. ...

  5. NABCD模型(猫咪记单词)

    项目需求分析与建议-NABCD模型(猫咪记单词) N (Need 需求) 对于现在的学生,尤其是大学生来说,学习英语是一件非常重要的事.我们有四级六级托福雅思等各种各样的英语方面的考试.而学习英语,很 ...

  6. 猫咪记单词——NABCD模型分析

    N --Need 需求:学习英语是一件非常重要的事.面对各种各样的考试,学习英语,最重要的就是词汇量,背单词是提高词汇量的最直接的方法,但是单纯的背单词太单调.寻找一些合适的,更易于接受的背单词学习英 ...

  7. 华为猫复活记(ADSL猫固件升级失败修复)

    回忆: 当偶N年前还是个菜菜时,瞎设置华为猫最后以除了power之外LED都不亮告终,晕啊!花200多块钱买的...还不会修(当时的猫捏么贵啊!),而且还不会修...... 自己去搜寻知识还有那台陪伴 ...

  8. 4.21-4.26旅行记之山城重庆(二)

    话外话:前几天,歪酷服务器老出问题,我的博客进不了.我当时一想,要是这博客就这么没了,我咋整?唉,肯定心里会觉得挺遗憾的,当然也仅仅是遗憾,有它固然好,没了,那不也算了,日子照样过. 在此,非常感谢歪 ...

  9. 宝付旅行记二(宁夏银川)

    第二天:会议开始的日子,7点不到就被拉起来直奔客户那里,充分发挥小忽悠的精神给客户洗脑,嘿嘿,忽悠完毕布置会场,忽然发现会场大家都各忙各的,我倒多余了,正好,跟朋友商量后下午自己安排.回到宾馆已然中午 ...

  10. 宝付旅行记三(宁夏银川)

    第三天:会议的第一天,早上5点钟就爬起来,梳洗完毕匆匆吃了早饭就直奔会场了,忙碌的一天,无话,晚上跟朋友一起来到了据说吃手抓非常正宗的同丰饭店,就在区政府斜对面,据说什么领导也常常下班过来,固定的点几 ...

最新文章

  1. JVM调优系列:(五)JVM常用调试参数和工具
  2. 申请Bing Search API
  3. 推荐 9 个爱不释手的 JSON 工具
  4. 【CodeForces - 305C】Ivan and Powers of Two(思维,STL,set,优先队列)
  5. 数据库每日一题 2020.05.07
  6. Clojure 学习入门(2)- eclipse 插件
  7. C# 操作IIS方法集合
  8. 基于python+django房屋租赁管理系统pycharm源码lw
  9. 腾讯新闻 React 同构直出优化实践
  10. 四六级考试中的计算机类文章,四六级英语考试进入机考时代
  11. Java基础篇--集合(collection)
  12. 《软技能》读书笔记——职业篇
  13. matlab模糊建模设计,毕业设计matlab建模
  14. 忘记Win10电脑密码,修改密码的方法
  15. DataGear 轻松制作支持图表联动的全国地图、省级地图数据可视化看板
  16. 算法日志:python把终端的信息存为log和logging
  17. S.M.A.R.T 参数详解及推荐指标
  18. 如何给电脑安装Windows双系统
  19. 共享内存(shmget函数详解)
  20. 必应输入法,搜狗输入法->当前日期快捷显示设置

热门文章

  1. CVE-2018-7490 uWSGI PHP Plugin目录遍历
  2. 前端知识总结之浏览器知识
  3. python帮室友避险——爬虫加可视化
  4. 第一章 .NET体系结构
  5. python自学多久-python自学多久
  6. Ceph 网络模块(1) - 网络模块基本结构
  7. [ProblemSolving]教育网下载速度慢,如何解决?
  8. windows xp\windows7\windows8\windows10\windows11原版镜像下载地址汇总
  9. 这个阿里网盘要下线了。。
  10. 基于Python实现的死链接自动化检测工具