一颗开花的树

谈笑但看风云起,龙腾尚待惊蛰春.

 

创建型模式----单件模式--singleton

1.保证一个类只有一个实例的机制.
2.站在类的设计者的角度,强制使一个类只能有一个实例,而不是站在类的使用者角度。

一:简单实现
//简单模式
class singletonOne
{
    
//静态变量
    private static singletonOne stOne = null;
    
//私有构造器
    private singletonOne(){}
    
//获取实例方法
    public static singletonOne getInstance()
    
{
        
if(stOne == null)
        
{
            stOne 
= new singletonOne();
        }

        
return stOne;
    }

}
优点是简单,清淅明了。缺点是在多线程环境下不能保证只实例化一次。如A,B两线程,同时判断stOne == null 为真,就会实例化两次。

二:线程安全
 1class singletonTwo
 2{
 3    //静态变量
 4    private static singletonTwo stTwo = null;
 5    //私有构造器
 6    private singletonTwo(){}
 7    //线程对象
 8    private static Object obj = new Object();
 9    
10    //获取实例方法1 完全保证线程安全,但增大了不必要的线程开销
11    public synchronized static singletonTwo  getInstance()
12    {
13        if(stTwo == null)
14        {
15            stTwo = new singletonTwo();
16        }

17        return stTwo;
18    }

19    
20    //获取实例方法2 当其它类或线程第二次来调用时,减少相应线程开销
21    public static singletonTwo getInstanceTwo()
22    {
23        if(stTwo == null)
24        {
25            synchronized(obj)
26            {
27                if(stTwo == null)//此处判断的作用在于:当第一次初始化时即有多个线程进入第一个   stTwo == null 的判断块,同时等待obj的线程释放。
28                {
29                    stTwo = new singletonTwo();
30                }

31            }

32        }

33        return stTwo;
34    }

35}
优点为:因为实例化语句处于getInstance方法里,即当需要一个singleton实例时,才会产生。这种方法称为惰性实例化,惰性实例化避免了在不必要一个实例时产生了实例对象。

三:静态初始化
//直接实例化一个静态实例
class staticSingletonOne
{
    
private static staticSingletonOne staticStOne = new staticSingletonOne();
    
public static int num = 0;
    
    
private staticSingletonOne()
    
{
        num 
= 10;
    }

    
    
public static staticSingletonOne getInstance()
    
{
        
return staticStOne;
    }

    
    
public static void SystemOutNum()
    
{
        System.out.println(num
++);
    }

    
public static void main(String[] str)
    
{
        staticSingletonOne.SystemOutNum();
        staticSingletonOne.SystemOutNum();
        staticSingletonOne.SystemOutNum();
        staticSingletonOne.SystemOutNum();
    }

}


//通过静态代码块实例化一个静态实例
class staticSingletonTwo
{
    
private static staticSingletonTwo staticStTwo;
    
public  static int num = 0;
    
    
private staticSingletonTwo()
    
{
        num 
= 10;
    }

    
    
static 
    
{
        staticStTwo 
= new staticSingletonTwo();
    }

    
    
public static staticSingletonTwo getInstance()
    
{
        
return staticStTwo;
    }

    
    
public static void SystemOutNum()
    
{
        System.out.println(num
++);
    }

    
    
public static void main(String[] str)
    
{
        staticSingletonTwo.SystemOutNum();
        staticSingletonTwo.SystemOutNum();
        staticSingletonTwo.SystemOutNum();
        staticSingletonTwo.SystemOutNum();
    }

}


//此两个类对于 singleton这个模式而言,产生的对象是没有任何区别的。
//同样只执行了一次staticStTwo = new staticSingletonTwo(),但输出的数字却有戏剧性的区别,staticSingletonOne输出的为0,1,2,3 而staticSingletonTwo输出的却为10,11,12,13。
//根本原因在于:staticSingletonOne在实例化对象时将 num赋为10,随后在执行静态变量初始化时又赋为了0。而在staticSingletonTwo, num 变量与实例化语句同处于静态变量中,先num=0,然后才赋num=10操作。



要点:
1.singleton不要支持序列化,避免出现多个实例,与singleton模式理念冲突
2.singleton只考虑到了对象的创建管理,没有考虑到对象的销毁管理,在支持垃圾回收的平台下(.net,java),一般不需要考虑对对象销毁管理作特别的处理。
3.模式的核心为:控制类的使用者对类的实例方法任意使用并使最终只产生一个实例。
4.普通实现方法,每次都需要检查类的对象是否已经存在,增大开销,建议使用静态初始化方法。

posted on 2007-12-28 00:34 泽来-王者之剑 阅读(1121) 评论(1)  编辑  收藏 所属分类: 设计模式系列

评论

# re: 创建型模式----单件模式--singleton 2007-12-28 09:05 happycat2007

You said very good,very detail!  回复  更多评论   


只有注册用户登录后才能发表评论。


网站导航:
 

导航

统计

常用链接

留言簿(4)

随笔分类

随笔档案

友情链接

搜索

最新评论