【问题标题】:Unity: NullReferenceException统一:NullReferenceException
【发布时间】:2013-07-22 08:33:27
【问题描述】:

NullReferenceException:对象引用未设置为对象的实例 Tower.OnGUI () (在 Assets/Tower.cs:100)

相关行是:

if(Main.Gold >= Towers.u[stage])

Towers中的变量是这样定义的,我做错了吗?

using UnityEngine;
using System.Collections;
using System.Collections.Generic;

public class Towers : MonoBehaviour {

    public static float[] d;
    public static float[] r;
    public static float[] s;
    public static float[] u;

    // Use this for initialization
    void Start () { 
        d = new float[10];
        d[0] = 1f;
        d[1] = 3f;
        d[2] = 5f;
        d[3] = 7f;
        d[4] = 9f;
        d[5] = 11f;
        d[6] = 13f;
        d[7] = 15f;
        d[8] = 18f;
        d[9] = 21f;
        d[10] = 23f;        

        r = new float[10];
        r[0] = 5f;
        r[1] = 9f;
        r[2] = 13f;
        r[3] = 17f;
        r[4] = 21f;
        r[5] = 25f;
        r[6] = 29f;
        r[7] = 33f;
        r[8] = 37f;
        r[9] = 41f;
        r[10] = 45f;

        s = new float[10];
        s[0] = 3f;
        s[1] = 2.8f;
        s[2] = 2.6f;
        s[3] = 2.4f;
        s[4] = 2.2f;
        s[5] = 2f;
        s[6] = 1.8f;
        s[7] = 1.6f;
        s[8] = 1.4f;
        s[9] = 1.2f;
        s[10] = 1f;

        u = new float[10];
        u[0] = 50f;
        u[1] = 100f;
        u[2] = 150f;
        u[3] = 200f;
        u[4] = 250f;
        u[5] = 300f;
        u[6] = 350f;
        u[7] = 400f;
        u[8] = 450f;
        u[9] = 500f;
        u[10] = 0f;     
    }
}

谢谢!

【问题讨论】:

标签: c# unity3d


【解决方案1】:

似乎Main 为空,或者您在导致问题的行之前没有调用Towers.Start()

当像这样初始化静态字段时,有时最好在声明字段的地方使用静态初始化,方法是调用返回初始化数据的私有静态方法。

这样做意味着您不需要单独的 Start() 方法,您必须记住调用该方法。

例如:

public class Towers: MonoBehaviour
{
    public static float[] d = initD();
    public static float[] r = initR();
    public static float[] s = initS();
    public static float[] u = initU();

    private static float[] initD()
    {
        return new []
        {
             1f,
             3f,
             5f,
             7f,
             9f,
            11f,
            13f,
            15f,
            18f,
            21f,
            23f
        };
    }

    private static float[] initR()
    {
        return new []
        {
             5f,
             9f,
            13f,
            17f,
            21f,
            25f,
            29f,
            33f,
            37f,
            41f,
            45f
        };
    }

    private static float[] initS()
    {
        return new []
        {
            3.0f,
            2.8f,
            2.6f,
            2.4f,
            2.2f,
            2.0f,
            1.8f,
            1.6f,
            1.4f,
            1.2f,
            1.0f
        };
    }

    private static float[] initU()
    {
        return new[]
        {
             50f,
            100f,
            150f,
            200f,
            250f,
            300f,
            350f,
            400f,
            450f,
            500f,
              0f
        };
    }
}

【讨论】:

    【解决方案2】:

    您应该将任何单声道行为的初始化放在 Awake 而不是 Start 中,Awake 是您可以在 MonoBehaviour 的生命周期中捕获的第一个事件。

    编辑:请记住,如果您尝试从 Awake 访问其他 MonoBehaviours,则无法确定它们是否已经初始化。

    【讨论】:

      【解决方案3】:

      您应该将 Start 函数中的行移到创建时调用的 Awake 函数。并且您尝试访问从 0 到 10 的数组,但数组大小为 10,因此您必须访问最多 9 个数组。如果要访问数组的第十个值,则必须将其分配为 11 大小表示值的实际计数。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2021-10-23
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-11-03
        • 2015-01-12
        相关资源
        最近更新 更多