设计模式的多种实现

单例模式的详情请关注《陈词滥调的单例》

饿汉式(立即加载)

package com.zuoyang.singleton;

/**
 * 饿汉式:
 *  * 线程安全,在线程还出现以前就是创建了对象
 *
 */
public class SingLetonHungry  {
    private static  SingLetonHungry singLetonHungry = new SingLetonHungry();
   private SingLetonHungry(){}
   public static SingLetonHungry getInstance(){
       return singLetonHungry;
   }
}

线程类

package com.zuoyang.singleton;

public class SingLetonHungryThread extends Thread {
    @Override
    public void run(){
 //        通过打印类的hashCode来确定是否为一个对象
        System.out.println(SingLetonHungry.getInstance().hashCode());
    }
}

运行类

package com.zuoyang.singleton;

public class SingLetonHungryRun {
    public static void main(String[] args) {
        SingLetonHungryThread singLetonHungryThread1 = new SingLetonHungryThread();
        SingLetonHungryThread singLetonHungryThread2 = new SingLetonHungryThread();
        SingLetonHungryThread singLetonHungryThread3 = new SingLetonHungryThread();
        singLetonHungryThread1.start();
        singLetonHungryThread2.start();
        singLetonHungryThread3.start();
    }
}

运行结果

[图片上传失败...(image-3f198-1563808417878)]

懒汉式(延迟加载)

线程不安全版

package com.zuoyang.singleton;

/**
 *  懒汉式单例,但是多线程的情况下不安全
 */
public class SinLetonLazyOne {
    //静态块,公共内存区域
    private static SinLetonLazyOne sinLetonLazyOne;

    private SinLetonLazyOne(){
    }
    //调用方法之前,先判断
    //如果没有初始化,将其进行初始化,并且赋值
    //将该实例缓存好
    public static SinLetonLazyOne getInstance(){
        if (sinLetonLazyOne!=null) {

        }else {
            //两个线程都会进入这个if里面
             sinLetonLazyOne = new SinLetonLazyOne();
        }
        //如果已经初始化,直接返回之前已经保存好的结果
        return sinLetonLazyOne;
    }
}

线程类

package com.zuoyang.singleton;

public class SinLetonlLazyOneThread extends Thread {

    @Override
    public void run(){
        System.out.println(SinLetonLazyOne.getInstance().hashCode());
    }
}

运行类

package com.zuoyang.singleton;

public class SinLetonlLazyOneRun {
    public static void main(String[] args) {
        SinLetonlLazyOneThread sinLetonlLazyOneThread1 = new SinLetonlLazyOneThread();
        SinLetonlLazyOneThread sinLetonlLazyOneThread2 = new SinLetonlLazyOneThread();
        SinLetonlLazyOneThread sinLetonlLazyOneThread3 = new SinLetonlLazyOneThread();
        sinLetonlLazyOneThread1.start();
        sinLetonlLazyOneThread2.start();
        sinLetonlLazyOneThread3.start();
    }
}

运行结果

[图片上传失败...(image-f13f59-1563808417878)]

synchronized关键字版

package com.zuoyang.singleton;

/**
 * 基于加锁的线程安全的懒汉式单例
 */
public class SinLetonLazyTwo {

    private static SinLetonLazyTwo sinLetonLazyTwo;

    private SinLetonLazyTwo() {
    }

    //加锁 来保证多线程的情况下也是一个单例
    synchronized public static SinLetonLazyTwo getInstance() {
        try {
            if (sinLetonLazyTwo != null) {
            } else {
                Thread.sleep(3000);
                sinLetonLazyTwo = new SinLetonLazyTwo();
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return sinLetonLazyTwo;
    }
}

线程类

package com.zuoyang.singleton;

public class SinLetonlLazyTwoThread extends Thread {

    @Override
    public void run(){
        System.out.println(SinLetonLazyTwo.getInstance().hashCode());
    }
}

运行类

package com.zuoyang.singleton;

public class SinLetonlLazyTwoRun {
    public static void main(String[] args) {
        SinLetonlLazyTwoThread sinLetonlLazyTwoThread1 = new SinLetonlLazyTwoThread();
        SinLetonlLazyTwoThread sinLetonlLazyTwoThread2 = new SinLetonlLazyTwoThread();
        SinLetonlLazyTwoThread sinLetonlLazyTwoThread3 = new SinLetonlLazyTwoThread();
        sinLetonlLazyTwoThread1.start();
        sinLetonlLazyTwoThread2.start();
        sinLetonlLazyTwoThread3.start();
    }
}

运行结果

[图片上传失败...(image-fddb4a-1563808417878)]

同步代码块版(线程不安全)

package com.zuoyang.singleton;

/**
 * 基于加锁的线程不安全的懒汉式单例
 */
public class SinLetonLazyTwoTwo {

    private static SinLetonLazyTwoTwo sinLetonLazyTwoOne;

    private SinLetonLazyTwoTwo() {
    }

    //加锁 来保证多线程的情况下也是一个单例

    public static SinLetonLazyTwoTwo getInstance() {
        try {

            if (sinLetonLazyTwoOne != null) {
            } else {
                Thread.sleep(3000);
                synchronized (SinLetonLazyTwoTwo.class) {
                    sinLetonLazyTwoOne = new SinLetonLazyTwoTwo();
                }
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return sinLetonLazyTwoOne;
    }
}

线程类

package com.zuoyang.singleton;

public class SinLetonlLazyTwoOneThread extends Thread {

    @Override
    public void run(){
        System.out.println(SinLetonLazyTwoOne.getInstance().hashCode());
    }
}

运行类

package com.zuoyang.singleton;

public class SinLetonlLazyTwoTwoRun {
    public static void main(String[] args) {
        SinLetonlLazyTwoTwoThread sinLetonlLazyTwoTwoThread1 = new SinLetonlLazyTwoTwoThread();
        SinLetonlLazyTwoTwoThread sinLetonlLazyTwoTwoThread2 = new SinLetonlLazyTwoTwoThread();
        SinLetonlLazyTwoTwoThread sinLetonlLazyTwoTwoThread3 = new SinLetonlLazyTwoTwoThread();
        sinLetonlLazyTwoTwoThread1.start();
        sinLetonlLazyTwoTwoThread2.start();
        sinLetonlLazyTwoTwoThread3.start();
    }
}

运行结果

[图片上传失败...(image-e2a319-1563808417878)]

DCL双检查锁机制版(Double-Check Locking)

package com.zuoyang.singleton;

/**
 * 基于双重检查锁的机制实现的单例模式
 */
public class SinLetonLazyThree {

    private static SinLetonLazyThree sinLetonLazyTwoOne;

    private SinLetonLazyThree() {
    }


    public static SinLetonLazyThree getInstance() {
        try {
//存在多个线程,跑进来在这里
            if (sinLetonLazyTwoOne != null) {
            } else {
                Thread.sleep(3000);
                //后面进来的线程需要判断lazy是否已经初始化了,不然的话,会重新创建新的对象
                synchronized (SinLetonLazyThree.class) {
                    if (sinLetonLazyTwoOne == null)
                        sinLetonLazyTwoOne = new SinLetonLazyThree();
                }
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return sinLetonLazyTwoOne;
    }
}

线程类

package com.zuoyang.singleton;

public class SinLetonlLazyThreeThread extends Thread {

    @Override
    public void run(){
        System.out.println(SinLetonLazyThree.getInstance().hashCode());
    }
}

运行类

package com.zuoyang.singleton;

public class SinLetonlLazyThreeRun {
    public static void main(String[] args) {
        SinLetonlLazyThreeThread sinLetonlLazyThreeThread1 = new SinLetonlLazyThreeThread();
        SinLetonlLazyThreeThread sinLetonlLazyThreeThread2 = new SinLetonlLazyThreeThread();
        SinLetonlLazyThreeThread sinLetonlLazyThreeThread3 = new SinLetonlLazyThreeThread();
        sinLetonlLazyThreeThread1.start();
        sinLetonlLazyThreeThread2.start();
        sinLetonlLazyThreeThread3.start();
    }
}

运行结果

[图片上传失败...(image-63ced0-1563808417878)]

使用静态内部类实现单例模式

package com.zuoyang.singleton;

public class SingLetonStatic {
    private static  SingLetonStatic singLetonStatic =null;

    private SingLetonStatic(){}

    static {
        singLetonStatic = new SingLetonStatic();
    }

    public static SingLetonStatic getInstance() {
        return singLetonStatic;
    }
}

线程类

package com.zuoyang.singleton;

public class SingLetonStaticThread extends Thread{
    @Override
    public void run(){
        for (int i = 0; i <5 ; i++) {
            System.out.println(SingLetonStatic.getInstance().hashCode());
        }
    }
}

运行类

package com.zuoyang.singleton;

public class SingLetonStaticRun {
    public static void main(String[] args) {
        SingLetonStaticThread singLetonStaticThread1 = new SingLetonStaticThread();
        SingLetonStaticThread singLetonStaticThread2 = new SingLetonStaticThread();
        SingLetonStaticThread singLetonStaticThread3 = new SingLetonStaticThread();
        singLetonStaticThread1.start();
        singLetonStaticThread2.start();
        singLetonStaticThread3.start();
    }
}

运行结果

[图片上传失败...(image-15f231-1563808417878)]

序列化与反序列化的单例模式

package com.zuoyang.singleton;

import java.io.Serializable;

public class SingLetonSerializable implements Serializable {

    private SingLetonSerializable(){}

    private static class SingLetonSerializableHandler{
        private static final SingLetonSerializable singLetonSerializable  = new SingLetonSerializable();
    }

    public static SingLetonSerializable getInstance(){
        return SingLetonSerializableHandler.singLetonSerializable;
    }

    protected Object readResolve(){
        return SingLetonSerializableHandler.singLetonSerializable;
    }
}

运行类

package com.zuoyang.singleton;

import java.io.*;

public class SingLetonSerializableSaveAndRead {
    public static void main(String[] args) {
        try {
            SingLetonSerializable singLetonSerializable = SingLetonSerializable.getInstance();
            FileOutputStream fileOutputStream = new FileOutputStream(new File("E://MyOne.txt"));
            ObjectOutputStream objectOutputStream = new ObjectOutputStream(fileOutputStream);
            objectOutputStream.writeObject(singLetonSerializable);
            objectOutputStream.close();
            fileOutputStream.close();
            System.out.println(singLetonSerializable.hashCode());
        }catch (FileNotFoundException e){
            e.printStackTrace();
        }catch (IOException e){
            e.printStackTrace();
        }

        FileInputStream fileInputStream = null;
        try {
            fileInputStream = new FileInputStream(new File("E://MyOne.txt"));
            ObjectInputStream objectInputStream = new ObjectInputStream(fileInputStream);
            SingLetonSerializable singLetonSerializable = (SingLetonSerializable)objectInputStream.readObject();
            objectInputStream.close();
            fileInputStream.close();
            System.out.println(singLetonSerializable.hashCode());
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }

    }
}

运行结果

[图片上传失败...(image-67ac5a-1563808417878)]

enum枚举实现单例模式

package com.zuoyang.singleton;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;

public class SingLetonEumOne {
    public enum SingLetonEumTest {
        connectionFactory;
        private Connection connection;
        private SingLetonEumTest(){
            try {
                Class.forName("com.mysql.jdbc.Driver");
                String url="jdbc:mysql://localhost:3306";
                String user="root";
                String password="root";
                connection = DriverManager.getConnection(url,user,password);
            } catch (ClassNotFoundException e) {
                e.printStackTrace();
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
        public Connection getConnection(){
            return connection;
        }
    }
    public static Connection getConnection(){
        return SingLetonEumTest.connectionFactory.getConnection();
    }
}

线程类

package com.zuoyang.singleton;

public class SingLetonEumThreadTest extends Thread {
    @Override
    public void run(){
        for (int i = 0; i <5 ; i++) {
            System.out.println(SingLetonEumOne.getConnection().hashCode());
        }

    }
}

运行类

package com.zuoyang.singleton;

public class SingLetonEumRunTest {
    public static void main(String[] args) {
        SingLetonEumThreadTest singLetonEumThreadTest1 = new SingLetonEumThreadTest();
        SingLetonEumThreadTest singLetonEumThreadTest2 = new SingLetonEumThreadTest();
        SingLetonEumThreadTest singLetonEumThreadTest3 = new SingLetonEumThreadTest();
        singLetonEumThreadTest1.start();
        singLetonEumThreadTest2.start();
        singLetonEumThreadTest3.start();
    }
}

运行结果

[图片上传失败...(image-70c9ae-1563808417878)]

GitHub地址

https://github.com/dxf1998/singleton.git
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 212,884评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,755评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 158,369评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,799评论 1 285
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,910评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,096评论 1 291
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,159评论 3 411
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,917评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,360评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,673评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,814评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,509评论 4 334
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,156评论 3 317
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,882评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,123评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,641评论 2 362
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,728评论 2 351

推荐阅读更多精彩内容

  • Swift1> Swift和OC的区别1.1> Swift没有地址/指针的概念1.2> 泛型1.3> 类型严谨 对...
    cosWriter阅读 11,093评论 1 32
  • 瑞·达利欧说:“我现在认识到自然会走向整体的最优化,而不是个体的最优化。但多数人只是根据事物对自身的影响判断好坏。...
    淼淼余波阅读 340评论 0 7
  • 今天是五月的最后一天,我希望它可过得慢点,虽然这31天都有异常的纠结和痛苦,不过目前已经恢复平静。但是还是需要自己...
    日记AS阅读 118评论 0 0
  • 孩子做卷子,一道题是忘了写完,一道题是忘了做,看的我一身恼火,可是想想老师教给我们的,稳! 好吧,先稳住。...
    幸福的小秋阅读 144评论 0 0
  • 经常有人留言问:运动坚持不下去,减肥没有动力肿么办? 还有人问有没有什么图片可以提供给她,设成桌面壁纸,每天一看就...
    叽里咕噜滚下来阅读 234评论 0 0