Which getters are hiding expensive side-effects?

Consider the expression:

transform.position = Vector3.zero;

The "transform" getter is hiding a GetComponent() side-effect and the "position" getter is hiding matrix-transformation side-effects. Yet, this is the syntax encouraged by the documentation and tutorials, even though it's suboptimal for per-frame computation.

I'm paranoid about which parts of my code should be precached. Are there any other getters to shy away from in Update() and FixedUpdate()?

All the other component accessor variables (listed here) will incur a GetComponent lookup, and are worth caching. Other than that, I wouldn't say that the setting .position cost is "hidden" as such, because you're setting the world position rather than the .localPosition so it's inevitably going to have to work this out in relation to its parent.

And in terms of the documentation - it's encouraged for simplicity, however this specific detail that you mention is covered in the manual page "Overview: Performance Optimization", which may answer a lot of your questions.

In particular, it states:

Whenever you access a component through GetComponent or an accessor variable, Unity has to find the right component from the game object. This time can easily be saved by caching a reference to the component in a private variable.

And it follows on by giving the example of caching the 'transform' component reference.

For more detail on optimising your projects, read the whole of that page, and also watch Joachim Ante's Unite presentation video, "Performance Optimization":


Something I found that was really expensive to set is transform.localScale. Avoid setting the scale of an object every frame unless it's actually changing.

Fortunately if you find that you're accessing a built-in reference type frequently, it's possible to cache the value without changing the interface (at least in C#). Granted, it's a pretty minor optimization compared to most game code, but at least in this case it's near-free.

Transform cachedTransform;
public new Transform transform
		if( cachedTransform == null )
			cachedTransform = GetComponent<Transform>();
		return cachedTransform;