`

单例模式在多线程下的问题

阅读更多
单例设计模式有两种形式:一种是饥饿式

Java代码 
package net.chopsuey.singleton;  

public final class EagerSingleton  
{  
   private static EagerSingleton singObj = new EagerSingleton();  
 
    private EagerSingleton()  
    {  
    }    
    public static EagerSingleton getSingleInstance()  
    {  
        return singObj;  
    }  

package net.chopsuey.singleton;

public final class EagerSingleton
{
    private static EagerSingleton singObj = new EagerSingleton();

    private EagerSingleton()
    {
    }

    public static EagerSingleton getSingleInstance()
    {
        return singObj;
    }
}

比较明显,这种是线程安全的。因为static变量是在类被加载时(有可能没被实例化)初始化并仅被初始化一次。因为这样就可以保证只有一个singObj被初始化。

另外一种则是懒汉式

Java代码 
package net.chopsuey.singleton;  
 
public final class LazySingleton  
{  
    private static LazySingleton singObj = null;    
    private LazySingleton()  
    {  
    }  
 
    public static LazySingleton getSingleInstance()  
    {  
        if (singObj == null)  
        {  
            singObj = new LazySingleton();  
       }  
        return singObj;  
    } 
package net.chopsuey.singleton;

public final class LazySingleton
{
    private static LazySingleton singObj = null;

    private LazySingleton()
    {
    }

    public static LazySingleton getSingleInstance()
    {
        if (singObj == null)
        {
            singObj = new LazySingleton();
        }
        return singObj;
    }

这种则是线程不安全的了。因为当有多个线程一起调用getSingleInstance()时则可能会生成多个实例。因此才需要修改一下。修改为我之前的那段代码

Java代码 
package net.chopsuey.singleton;    
  
public class Singleton    
{    
    private static class SingletonHolder    
    {    
       static Singleton instance = new Singleton();    
    }    
   
    public static Singleton getInstance()    
    {    
        return SingletonHolder.instance;    
    }    

package net.chopsuey.singleton; 

public class Singleton 

    private static class SingletonHolder 
    { 
        static Singleton instance = new Singleton(); 
    } 

    public static Singleton getInstance() 
    { 
        return SingletonHolder.instance; 
    } 
}
一个静态内部类内的一个静态成员就可以保证它只在类被加载时只初始化一次。因此不管有多少个线程来调用它,都只能得到同个实例(类被加载时初始化的那个)。

分享到:
评论

相关推荐

    C++ 多线程和多线程下的单例模式

    本资源描述了C++11 中多线程的创建,C++11中std命名空间中将boost库中的Thread加入,boost多线程从准标准变为标准,其中还介绍了C++ 多线程下的单例模式的使用,本文档为txt文档

    多线程单例模式并发访问

    深入浅出:讲解单例模式,多线程安全和并发访问问题.让你轻松应对面试

    QT单例模式、多线程、双重校验加锁

    QT实现单例模式多线程及双重校验加锁的应用demo

    多线程并发下的单例模式-源码

    该资源是多线程并发下的单例模式-源码,几乎包含了所有方式实现的单例模式,并且能够确保在多线程并发下的线程安全性。 读者可结合本人博客 http://blog.csdn.net/cselmu9?viewmode=list 中的《线程并发之单例模式...

    多线程下的单例模式优化

    这是一个关于多线程下的单例模式优化代码。public class Singleton { private static Singleton instance; private Singleton (){ } public static Singleton getInstance(){ //对获取实例的方法进行同步 if...

    单例模式,single

    在本月的专栏中,David Geary探讨了单例模式以及在面对多线程(multithreading)、类装载器(classloaders)和序列化(serialization)时如何处理这些缺陷。 单例模式适合于一个类只有一个实例的情况,比如窗口管理器...

    单例模式下,使用多线程实现

    单例模式下,使用多线程实现

    Java多线程实战之单例模式与多线程的实例详解

    今天小编就为大家分享一篇关于Java多线程实战之单例模式与多线程的实例详解,小编觉得内容挺不错的,现在分享给大家,具有很好的参考价值,需要的朋友一起跟随小编来看看吧

    Qt多工程调用单例实现,带线程锁

    本资源包含有三个子项目工程,实现的是通过DataSource做数据管理,DataSource是一个单例类,做了测试在不同类中调用单例函数依旧能保证唯一性

    7种单例模式

    设计模式之七种单例模式代码及ppt,包含多线程环境测试和反序列化测试

    c++单例模式线程日志类

    自己写的c++实现的单例模式日志类。支持多线程、日志等级、可输出每条日志的输出时间(精确到毫秒级),日志级别,支持可变长参数、标准格式化输出。 代码中包含VS2010示例程序,使用方便。

    Java多线程-解决单例模式中的懒汉式的线程安全问题

    Java多线程--解决单例模式中的懒汉式的线程安全问题

    单例模式连接数据库步骤

    单例模式连接数据库步骤是指在Java项目中使用单例模式来连接数据库的步骤。单例模式是一种设计模式,它可以确保一个类只有一个实例,并提供了一个全局访问点来访问这个实例。在连接数据库时,单例模式可以确保数据库...

    设计模式经典案例之单例模式

    单例模式主要有懒汉式和饿汉式两种实现,饿汉式不会有线程安全的问题,但是提前构造对象占用了一定...懒汉式应使用DCL机制来避免多线程竞争资源的问题,并且懒汉式可以在需要使用对象的时候才去创建对象,节省了资源。

    Java 单例模式 懒汉模式

    Java 单例模式 懒汉模式 //懒汉式 多线程中不可以保证是一个对象

    单例模式详解.pdf

    2、掌握 IDEA 环境下的多线程调试方式。 3、掌握保证线程安全的单例模式策略。 4、掌握反射暴力攻击单例解决方案及原理分析。 5、序列化破坏单例的原理及解决方案。 6、掌握常见的单例模式写法。

    C++实现的单例模式代码

    本人使用C++实现的单例模式,实现方式有三种,包括单线程下的,多线程下的代码。

    java单例模式完全剖析

    单例模式是最简单的设计模式之一,但是对于Java的开发者来说...在本月的专栏中,David Geary探讨了单例模式以及在面对多线程(multithreading)、类装载器(classloaders)和序列化(serialization)时如何处理这些缺陷。

    Qt两种方法实现多线程并安全结束线程及QMutex加锁Qt单例化实现

    Qt两种方法实现多线程的开启,及子线程的安全结束线程,及QMutex加锁,Qt单例化实现

    单例模式讲解说明与实例

    另一个解决方案是使用双重检查锁定机制(Double-Checked Locking)来实现线程安全的单例模式。这种方法可以减少 synchronize 的使用,从而提高系统的性能。 ```java public class Singleton { private volatile ...

Global site tag (gtag.js) - Google Analytics