U3D点滴-单例模式

来源:互联网 发布:做淘宝月收入多少 编辑:程序博客网 时间:2024/05/25 20:00

例如:对于一个音乐管理类

usingUnityEngine;
 
publicclass MusicManager : MonoBehaviour
{
    publicvoid Play()
    {
        //Play some audio!
    }
}

现在要调用来播放音乐,如下代码

Object.FindObjectOfType < MusicManager > ().Play();

以上的代码不仅难懂而且不安全,比较的好方式如下代码:

var musicManager = Object.FindObjectOfType < MusicManager >();

if ( musicManager != null )

{

musicManager.Play ();

}

以上的代码运行没有问题,但是每次调用的话会比较麻烦。


现在就用单例模式来创建代码:


publicclass MusicManager : MonoBehaviour
{
    //We make a static variable to our MusicManager instance
    publicstatic MusicManager instance { get;privateset; }
 
    //When the object awakens, we assign the static variable
    voidAwake()
    {
        instance = this;
    }
 
    publicvoid Play()
    {
        //Play some audio!
    }
}
 
//...
//Now in another class, we can call Play() by using the static variable!
publicclass LevelController : MonoBehaviour
{
    voidPlayMusic()
    {
        MusicManager.instance.Play();
}
}
这样的方式叫做lazy Singleton(偷懒的单例模式吗?!)
这样使用要注意一个地方就是调用的时间,就是如果要使用不能在awake()方法里面,以保证这个实例不为null
比如,Start()方法就可以。

以下是标准的单例模式
publicclass MusicManager : MonoBehaviour
{
    //Here is a private reference only this class can access
    privatestatic MusicManager _instance;
 
    //This is the public reference that other classes will use
    publicstatic MusicManager instance
    {
        get
        {
            //If _instance hasn't been set yet, we grab it from the scene!
            //This will only happen the first time this reference is used.
            if(_instance == null)
                _instance = GameObject.FindObjectOfType<MusicManager>();
            return_instance;
        }
    }
 
    publicvoid Play()
    {
        //Play some audio!
    }
}


持续的单例
有时候你可能要在不同的场景里面使用单例
publicclass MusicManager : MonoBehaviour
{
    privatestatic MusicManager _instance;
 
    publicstatic MusicManager instance
    {
        get
        {
            if(_instance == null)
            {
                _instance = GameObject.FindObjectOfType<MusicManager>();
 
                //Tell unity not to destroy this object when loading a new scene!
                DontDestroyOnLoad(_instance.gameObject);
            }
 
            return_instance;
        }
    }
 
    voidAwake()
    {
        if(_instance == null)
        {
            //If I am the first instance, make me the Singleton
            _instance = this;
            DontDestroyOnLoad(this);
        }
        else
        {
            //If a Singleton already exists and you find
            //another reference in scene, destroy it!
            if(this!= _instance)
                Destroy(this.gameObject);
        }
    }
 
    publicvoid Play()
    {
        //Play some audio!
    }
}


DontDestroyOnLoad() will maintain all scripts that are placed on the same GameObject as your singleton.

 For this reason it’s usually a good idea to put a singleton on it’s own GameObject alone.

Other Notes:

  • DontDestroyOnLoad() only needs to be used on objects inheriting MonoBehaviour. A static reference in a normal class will maintain its data across scenes.
  • In Unity, if you have a reference to a GameObject or MonoBehaviour that has been destroyed, it will equal null. The singleton examples above use this to their advantage.
以上是e文,自己体会吧


原文引用:http://unitypatterns.com/singletons/


0 0
原创粉丝点击