来次面试吧?准备好没,GO!

  1. 问:自我介绍下吧。(开个玩笑。。。往下)请问你用过单例模式吗?什么是单例?
  2. 答:用过啊,单例模式就是只创建一个实例。
  3. 问:噢?那是单线程,还是多线程下都是呢?
  4. 答:这个类在JVM里就一个实例(这样回答也许会更好)
  5. (注:通常面试官,到这里,就会让你写一个单例,当然我们不,你看这篇文章,就是不让你再网上找其他重复的资料了。)
  6. 问:说说你用的场景吧
  7. 答:........
  8. 问:说说单例的几种类型?或者说何时对实例的初始化?
  9. 答:........
  10. 问:画过单例的类图吗?会画吗?
  11. 答:(需要吗?)
  12. 问:写个单例的实现吧?

类名:SingleTon

实例:uniqueInstance 简称ust吧。(这里我插入一句编程规范:起名不要吝惜把实例代表的意思表达清楚,名字可稍微长点,这里就是想偷懒)

实现1:

  1. public class Singleton{
  2. private final static Singleton ust = new Singleton();
  3. private Singleton() {}
  4. public static Singleton getInstance(){
  5. return ust;
  6. }
  7. }

注:这里顺便说明一下语法。通常final与static同时出现,习惯让final在前

分析:

1. 这里需要加final吗? 是的,因为java反射,可以改变private描述的变量

2. 有书里把这种方式称为饿汉单例模式(另一个种叫懒汉单例),并且已经为人所接受

3. 在多线程方面表现出了他优势,不需要担心方法重复里延时创建带来的原子性(这样说难理解,其实就是出现两个或多个实例)

4. 这个,不符合我们习惯的 用到时再实例化的原则(不过这没关系。。。)

看,其实你发现这还是个不错的单例,那么其实有个最好的实现,最好的实现:

单元素的枚举类型已经成为Singleton的最佳实践

即使面对复杂的序列化或者反射攻击,绝对防止多次实例化,还有他的简洁和优雅。

----好吧,面试结束了。 其实你对单例的理解还是不错的,而且你已经得到了最好的答案,有兴趣彻底玩转单例吗,继续听我唠叨。


我们看看懒汉单例模式:

实现2:

  1. public class Singleton{
  2. // private final static Singleton ust = null;
  3. // 不该加final,这里明显有偷懒嫌疑,复制上面的例子,又测试不够,以后尽量避免类似问题。
  4. // 8月15日修正
  5. private static Singleton ust = null;
  6. private Singleton(){}
  7. public staic Singleton getInstance(){
  8. //建议null==ust的方式,能帮助更快的发现错误。
  9. //部分老程序员的习惯,其实许多IDE会发现些低级错误。
  10. if(ust==null){//A
  11. ust = new Singleton();//B
  12. }
  13. return ust;
  14. }
  15. }

分析:

1. 懒汉模式,做到了需要时创建实例

2. 他遇到了尴尬的问题,因为当两个线程分开运行到A,然后进入了if块,可能就创建了2个实例,草稿的是,你已经初始了一些数据。

改进一下:

实现3:

  1. public class Singleton{
  2. private volatile static Singleton ust;
  3. private Singleton(){}
  4. public staic Singleton getInstance(){
  5. synchronized(Singleton.class){
  6. if(ust==null){
  7. ust= new Singleton();
  8. }
  9. }
  10. return ust;
  11. }
  12. }

分析:

1. 如果你不理解synchronized 的位置,就不用单例模式这么多写法,不如学习基础

2. volatile 确保ust被实例化后,多个线程正确处理。他失去了JVM必要的代码优化,如果不是多线程,就不要用

3. 这个叫做 “双检查加锁”,单例最后一种方式


综合讨论会:

  1. 小明: 单例目前一共谈到懒汉和饿汉两种,还有双检查加锁,最好的应该是单元素的枚举类型
  2. 小刚: 是的,回答了开头说的几种单例,那么哪些场景应该用单例呢?
  3. 小明: 我知道,有线程池,缓存,处理偏好设置,注册表,日志对象等等
  4. 小刚: 对,我对java比较了解,我知道Runtime.getRuntime()。
  5. C(为吗我叫C):我知道有java.lang.reflect.Proxy类
  6. 小明:有什么共同点呢,为什么用?是遵循对象尽量少创建原则?
  7. C:这是什么意思?
  8. 小刚:这很简单,不过这说法有点问题。因为对象占内存,有要造成垃圾回收,GC的时候JVM可是只干这个麻烦事
  9. 小明:是啊!
  10. 小刚:我想我知道,某些对象最好只有一个实例,多了会有问题产生。
  11. C:什么问题?
  12. 小刚:比如缓存,你从哪个实例里拿缓存呢?
  13. 小明:是的啊。。。

结束讨论会,总结一下吧。不,等等,还要补充两句: 
1. 单例模式定义:确保一个只有一个实例,并提供一个全局访问点

2. 如果getInstance()方法对应用程序不会额外负担,或者说影响不大,那写成怎样,其实没太大所谓。但是如果频繁运行,就要仔细考虑,因为一个同步,可能使得执行效率下降100倍

继续总结,还差个UML图呢,不妨在上个枚举的例子吧,枚举构造器默认私有吗?


枚举就算了,是不是默认构造器,自己研究下吧。。。呵呵

这回真总结了: 
1. 单例,有懒汉,饿汉,双检查加锁3种常见用法 
2. 单例模式,是因为如果多了,会造成数据遗漏等麻烦 
3. 最好的单例,单元素的枚举类型

呵呵,其实,就这些,本来想先写工厂的,因为去面试,遇到某些对单例了解比较浅,解释起来费劲,于是先以单例开篇,请关注下篇工厂模式。

本文转自 wws5201985 51CTO博客,原文链接:http://blog.51cto.com/yjplxq/931861,如需转载请自行联系原作者

我是架构师--设计模式-单例模式相关推荐

  1. 我是架构师-设计模式-工厂模式-工厂方法

    有款游戏叫模拟人生,我这里就例子就叫北漂人生吧. 北漂人生 规定安家模式 a.结婚 b.买房 c. 买车 d. 生娃 先看几种情况: 1. 我初来帝都,按照北漂人生规则,如果要安家,要遵守 a. 结婚 ...

  2. 我是架构师-基本类型-float

    讲述float这个类型确实让我有点没有头绪,但还是简单说下. 关于最大值最小值问题 Float.MAX_VALUE = 0x1.fffffeP+127f; Float.MIN_VALUE = 2-14 ...

  3. 【架构师李肯】带你走进架构师的一天

    作者简介 架构师李肯(全网同名),一个专注于嵌入式IoT领域的架构师.有着近10年的嵌入式一线开发经验,深耕IoT领域多年,熟知IoT领域的业务发展,深度掌握IoT领域的相关技术栈,包括但不限于主流R ...

  4. 架构师进阶之独孤九剑:设计模式详解

    我们继续架构师进阶之独孤九剑进阶,目前我们仍然在第一阶段:程序设计和开发环节. " 设计模式不仅仅只是一种规范,更多的是一种设计思路和经验总结,目的只有一个:提高你高质量编码的能力.以下主要 ...

  5. 【Java架构师面试题】设计模式面试专题(共35题含答案)

    设计模式(DesignPattern)是前辈们对代码开发经验的总结,是解决特定问题的一系列套路.它不是语法规定,而是一套用来提高代码可复用性.可维护性.可读性.稳健性以及安全性的解决方案. 本篇为设计 ...

  6. Java架构师,大数据架构师,高并发设计模式,机器学习知识点分享

    第一章:java精品课程目录大全 1.亿级流量电商详情页系统的大型高并发与高可用缓存架构实战 1课程介绍以及高并发高可用复杂系统中的缓存架构有哪些东西?32分钟 2基于大型电商网站中的商品详情页系统贯 ...

  7. C++ 设计模式原理与实战大全-架构师需备课程-夏曹俊-专题视频课程

    C++ 设计模式原理与实战大全-架构师需备课程-716人已学习 课程介绍         C++属于难学易用的工程开发语言,C++繁复的语法往往使得开发人员过于强调细节而缺乏软件体系结构的大局观.特别 ...

  8. 我是怎样成长为系统架构师的

    来这家公司从事信息化工作已经也有三个年头了,有必要对这三年的工作和成长以及不足之处做一个总结.在此之前,从2001年開始学习JAVA,那时候用Struts的开发的企业也不多,而我在的做项目的企业当时已 ...

  9. 优秀架构师养成记:我是如何逆袭走向“人生巅峰”的?

    大家好,我叫金泽,架构师一枚. 我的成长轨迹跟大多数人一样,平凡而曲折.二本大学毕业的我,机缘巧合之下报名了某Java 培训,结束后便直接进入东软,开启了人生第一份工作,一待就是 3 年.后来,怀揣着 ...

最新文章

  1. Oracle CBO 与 RBO
  2. EBS   常见的AD命令
  3. linux vim编辑器的用法
  4. ELK学习5_ELK文档资料:《ELK stack 权威指南/饶琛琳》推荐
  5. Blazor WebAssembly 3.2.0 已在塔架就位 将发射新一代前端SPA框架
  6. java 发送16进制数据'_java 16进制数据递增
  7. java 图形题,20140314 java练习题-打印各种图形
  8. 手机的寿命到底是多久,你多长时间换一次手机?
  9. android app报错log,Android studio 解决logcat无过滤工具栏的操作
  10. Mac 版 QQ 音乐上线离线提示音的方法?
  11. 群晖通过WebDAV挂载阿里云盘
  12. 台达b3伺服modbus通讯_台达ASDA-AB伺服与EVIEW触摸屏MODBUS通讯
  13. Android Studio 3.4.1设置背景颜色为保护色
  14. 上传 visio 2003 基本形状图谱
  15. 取代奶瓶Minidwep-gtk破解WPA 全攻略
  16. 从入门到冠军 中国移动人群画像赛TOP1经验学习研究
  17. IE主页遭篡改解决方法
  18. 田园综合体建设指导手册
  19. 2020牛客国庆集训派对day3
  20. 2021李林精讲精练880题 【数学二 解析分册】

热门文章

  1. 2个点马氏距离计算实例_数据分析基础:距离度量方式(欧式距离、马氏距离、曼哈顿距离)...
  2. BciPy: 一款基于Python用于BCI研究的开源软件
  3. 该项研究降低了使用大脑信号控制机器人手臂的位置误差
  4. 即将到截止日期,Frontiers期刊向您邀稿啦!脑机接口领域
  5. psychopy: pyglet.media.sources.riff.WAVEFormatException: AVbin is required to decode compressed medi
  6. AI发现人类肾细胞有一半结构未知,UCSD最新研究登上Nature,算法已开源
  7. MindSpore布道师队伍招募开始,助力小白成为大牛!
  8. 「人民的希望」首批临床结果公布:2/3重症10天内有效改善,一半以上摆脱呼吸机 | 新英格兰医学重磅...
  9. 刚刚,旷视开源深度学习框架「天元」:Brain++内核,研发和落地都在用;孙剑:COCO三连冠背后的秘密武器...
  10. IntelliJ IDEA(2017)安装和破解