Unity3D中多种单例模式的实现方式

Unity3D中多种单例模式的实现方式

日常瞎捣鼓,人比较懒,偶尔才写文章跟大家分享自个所学到的知识。希望对大家有帮助。

1、类中单例(基础版)

    public class GameManager
    {
        private static GameManager instance;    //单例对象,全局唯一

        public static GameManager GetInstance   //获取接口,也可以写成函数形式
        {
            get
            {
                if (instance == null)
                    instance = Activator.CreateInstance();
                return instance;
            }
        }

        public void Init()
        {
            Debug.Log("Initialized");
        }
    }




    /// 
    /// 调用方式
    /// 
    GameManager.GetInstance.Init();

优点:代码简单,实现方式简单。

缺点:项目中若需要很多类的单例来支撑的话,使用这种方式会让我们编写很多无用的重复代码(每个类都要实现一遍)

适用场景:适合单例使用较少的项目。




2、泛型单例(进阶版)

using System;
    public class Singleton< T > where T : class, new()
    {
        private static T instance = default(T);
        public static T GetInstance()
        {
            if (instance == null)
            {
                instance = new T();
            }
            return instance;
        }

    }
/// 
/// 具体类的定义
/// 
public class GameManager : Singleton  
{
    /// 
    /// 初始化游戏
    /// 
    public void InitGame()
    {
        ///init local data
        Debug.Log("Initailized");
    }
}

/// 
/// 使用方式
/// 
GameManager.GetInstance().InitGame();

优点:代码相对简单,只需要继承Singleton类就可以实现单例类。

缺点:因为泛型约束中填写了new(),因此子类无法私有化构造函数,子类依然可以通过new来实例化对象。

适用场景:适合单例使用较多的项目。





3、“实例化”型单例(只针对U3D,针对特殊需求)

    using UnityEngine;
    public class SingletonWithObj : MonoBehaviour where T : class  //不需要再这里加new()的泛型约束
    {
        private static T instance = default(T);

        public static T GetInstance()
        {
            if (instance == null)
            {
                GameObject go = new GameObject(typeof(T).ToString());    //第一次调用GetInstance时实例化一个U3D的空对象,并挂载单例管理脚本
                DontDestroyOnLoad(go);
                instance = go.AddComponent(typeof(T)) as T;
            }
            return instance;
        }
    }
/// 
/// 实现方法
/// 
public class ScenesManager : SingletonWithObj
{
    private ScenesManager() { }

}
//当这一语句被第一次调用的时候会自动创建U3D的空对象,并自动挂载当前场景管理脚本
ScenesManager.GetInstance();

优点:在单例进阶版的基础上改进,会在U3D中创建一个空对象并把对应的管理器脚本挂上去,从而对游戏进行

          相应的“特殊”管理。

缺点:必须得调用一次GetInstance才会创建对象。

使用场景:需要在游戏中生成一个空对象(挂载相应的管理脚本)用来实时管理游戏状态的情况。





不足:

1、针对第二点,子类无法声明 私有化的构造函数,导致该类依然无法禁止外部实例化。

2、针对第三点,无法让程序自动生成空对象,还得需要程序员去手动调用一次GetInstance()。

3、若有大神知道如何解决以上2点,望不吝赐教。谢谢!

你可能感兴趣的:(【Unity3D,原创笔记系列】)