获取GameObject参考的最快方法

时间:2017-05-24 23:09:48

标签: c# unity3d unity5 gameobject

获取GameObject参考的最快方法。

enter image description here

2 个答案:

答案 0 :(得分:1)

在Unity 4.x及更低版本中,缓存方法会明显加快。在这些版本中,MonoBehaviour.transform和MonoBehaviour.gameObject实际上不是字段;相反,“引擎盖下”它们表现得像附加存取器的属性。

因此,访问gameObject属性将通过访问器对Component.get_gameobject()进行方法调用。当然,方法调用自然会比简单的内存访问带来更多的开销。 (变换更糟糕;显然访问者实际上调用了GetComponent方法来返回值!)

这就是为什么你经常会看到经验丰富的Unity开发人员缓存这些值。

我有充分的权威,在Unity 5中简化了这个过程以获得更好的性能;使用内置属性仍然会产生非常小的开销,但据报道它是无关紧要的。

来源:https://blogs.unity3d.com/2014/06/23/unity5-api-changes-automatic-script-updating/

答案 1 :(得分:1)

我认为缓存变量比使用Component类中的gameObject变量更快,并且一个简单的测试证明是真的。这是因为缓存它会为您提供参考,而不是使用gameObject使用get访问器来返回引用。不确定获取引用是否需要本机函数调用,但这是可能的。使用get访问者比直接引用访问速度慢。

假设您有100万个脚本调用gameObject.activeSelf或通过缓存版本_GameObject.activeSelf

测试结果:

  

gameObject:54 ms

     

缓存_GameObject:30 ms

软件/硬件测试:

  • Unity 5.6.0f3
  • Windows 10 Pro
  • MacBookPro11,4
  • 16 GB RAM

重要吗?

在普通应用中,也许不是。在游戏中,是的。从游戏中删除24ms是一项很好的改进,具体取决于游戏类型。

测试脚本:

public GameObject _GameObject;

void Start()
{
    Application.runInBackground = true;

    int iterations = 1000000;

    //TEST 1
    Stopwatch stopwatch1 = Stopwatch.StartNew();
    for (int i = 0; i < iterations; i++)
    {
        bool active = gameObject.activeSelf;
    }
    stopwatch1.Stop();

    //TEST 2
    Stopwatch stopwatch2 = Stopwatch.StartNew();
    for (int i = 0; i < iterations; i++)
    {
        bool active = _GameObject.activeSelf;
    }
    stopwatch2.Stop();
    //SHOW RESULT
    WriteLog(String.Format("gameObject: {0}", stopwatch1.ElapsedMilliseconds));
    WriteLog(String.Format("Cached _GameObject: {0}", stopwatch2.ElapsedMilliseconds));
}

void WriteLog(string log)
{
    UnityEngine.Debug.Log(log);
}