Fastest way to get GameObject reference
In Unity 4.x and below, the caching method will be significantly faster. In these versions, MonoBehaviour.transform and MonoBehaviour.gameObject were not actually fields; rather, "under the hood" they behaved like properties with an accessory attached.
Thus, accessing the gameObject property will call the Component.get_gameobject () method through the accessor. Of course, method invocation naturally introduces additional overhead than simple memory access. (The transformation was worse, apparently the accessor actually called the GetComponent method to return a value!)
This is why you will often see Unity developers-Unity developers cache these values.
I have good credentials that this process has been optimized in Unity 5 to improve performance; using inline properties will still generate very little overhead, but reportedly negligible.
Source: https://blogs.unity3d.com/2014/06/23/unity5-api-changes-automatic-script-updating/
source to share
I assumed that caching a variable is faster than using a variable gameObject
from a class Component
, and a simple test showed that to be true. This is because caching will give you a link instead of using gameObject
that uses an accessory get
to return the link. Not sure if getting a reference requires a custom function call, but it is a possibility. Using get
accessor is slower than direct link access.
Let's say you have 1 million scripts calling gameObject.activeSelf
or through the cached version _GameObject.activeSelf
.
Test result:
gameObject:
54
msCached _GameObject:
30
ms
Software / hardware tested for:
- Unity 5.6.0f3
- Windows 10 Pro
- MacBookPro11.4
- RAM 16 GB.
Does it matter?
In a normal application, perhaps not. In the game, yes. Removing 24ms
from the game is a nice improvement depending on the type of game.
Test script:
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);
}
source to share