Unity开启协程失败的问题

开启协程必须继承MonoBehaviour,然后将其挂载到游戏物体上,这些是必要条件。但是笔者最近遇到一个问题就是这些条件都是成立的开启协程还是失败,最后引发出对静态对象的思考,接下来是引发错误原因的断点截图:

可以看到这个this竟然是null,这个脚本确实是挂载到一个物体上的,大概是下面代码段的原因导致出现这个错误的

public class SceneMonomerMgr : MonoBehaviour
{
    public static SceneMonomerMgr SmManger { get;private  set; }
    static SceneMonomerMgr()
    {
        if (SmManger == null)
            SmManger = new SceneMonomerMgr();
    }
    ...

this相当于挂载这个脚本的场景物体,使用饿汉形式的单例模式去强行创建出实例,会丢掉this的引用也难怪,并且这个是一个单例对象,只存在唯一的这个实例,估计把这个单例模式去掉也不会报错了(协程还有比较坑的地方是会受到Time.timeScale值的影响,大家需要注意一下的),但是因为这个脚本是一个管理器需要使用单例模式,所以准备Awake里面去给SmManger赋值,修改过之后代码如下:

public class SceneMonomerMgr : MonoBehaviour
{
    public static SceneMonomerMgr SmManger { get;private set; }
    void Awake()
    {
        SmManger = this.GetComponent<SceneMonomerMgr>();
    }
    ...

运行确实没有报错,接下来思考一下静态对象的一些作用,静态对象是唯一存在的,比如一个类创建n个实例,这个类中有一个成员是静态的,这个静态成员是共用的,n个实例只有这一个静态成员,接下来是代码段证明一下:

public class demo
{
    public static int a;
    public int b;
}
public class Test : MonoBehaviour
{
    void Awake()
    {
        demo d = new demo();
        demo.a = 1;
        d.b = 2;
        demo d1 = new demo();
        demo.a = 10;
        d1.b = 11;
    }
}

可以看到不能用d.a这个实例去访问a这个静态对象会报错的,只能用类的限定名去访问这个对象,这样就已经证明了上面所述的,什么情况下类要声明一个静态成员呢,比如有n个按钮,只有一个按钮是存在选中状态的,当a按钮出现选中状态的时候,其他按钮要去掉选中的状态,这样可以使用一个Int值表明当前那个按钮是被选中的,这个ini是共用的如果不是和当前自身索引一样就去掉选中状态。

发布了26 篇原创文章 · 获赞 3 · 访问量 1万+

猜你喜欢

转载自blog.csdn.net/m0_37920739/article/details/90511125