Effeciency and Best Practices

Ok, I’m fairly new to the community and, to be honest, still haven’t even got my iMac in the mail yet – however, it will be here next week.

So, onto my questions … when I am all setup and ready to go, I have quite a few scripts I need to write fairly quickly and I was wondering what the best way to approach scripting in Unity is.

I plan to develop using C# and am hoping to be able to bring with me a good bit of my general practices from my regular development job – this would be, reusable code.

So … for the purposes of Unity, is it better to write an extremely long script where all the heavy logic is buried inside of the Update/FixedUpdate or event callbacks … or is it OK to create a large call stack and have a bunch of smaller reusable scripts attached to game objects.

For instance, say I have a series of AI Logic snippets, and in “Game A” I want to use Logic Steps 3-6 and in “Game B” I want to use 1-10 … I can break the logic “steps” out into their own separate scripts and attached the portions of it to the objects that need them … but in doing so, each object now has 1-10 (or possibly even 100’s) of little scripts attached to it …

So basically, my question is … as Unity is a Game Engine and it already takes a good toll on the system resources to do the internal work, and frame rates are always of the utmost importance in most cases, is a lengthy call stack a serious performance issue or a negligible one?

In the case of the AI script, what I would actually wind up doing is creating maybe a few scripts that had totally different logic and then break the ‘steps’ out into if/switch conditionals within the script and toggling them through the Inspector with public vars … so, it was probably a poor example, but I hope I made my point as far as the logic is concerned.

My hope is, I can make a series of scripts that are reusable and just have a ‘library’ of game scripts that I can quickly access and attach to objects or allow my game designer to attach and configure … allowing me to remove myself from the actual game logic as much as possible and just write the core functionality and expose the variable data through the Inspector … eventually winding up with a long list of agnostic scripts that can be used for just about any purpose, just configure them as you need them…

Now … I understand, my overall question might be a ‘duh’ thing … I’m already assuming I can do this with Unity from my existing experience … just curious whether or not it’s a viable approach, or if I should rethink my overall approach and go another way.

Thanks

The rule of thumb is that if you can split a script up, and the splitting makes sense and results in versatility, the overhead incurred by there being more than one script is utterly negligible.

In practice, you can actually be quite inefficient and still get very good performance for most normal code. Things like the difference between spreading code across several scripts versus having one big monolithic script are generally of little importance in terms of performance (although you might want to go one way or the other for design reasons). You shouldn’t be afraid of the cost of function calls or calls from one script to another.

Where you actually have performance problems, the best thing to do is to avoid expensive calls (such as GetComponent) in tight loops, and to reduce the amount of code that is executed overall by virtue of using appropriate algorithms.

With regards to the organisational part of your question, I prefer to try to make each script as standalone as possible, so that it performs one useful task (or set of tasks) which can be reused anywhere and in conjunction with anything else, with minimum communication required with other scripts. Obviously, that’s an ideal which isn’t always attainable, so much of your game code will end up being a group of interrelated scripts in any case.

I appreciate the responses, and am now a bit more confident that I can work on my ‘script library’ with or without really knowing what the overall outcome of the game mechanics are going to be (largely since we’ll be trying to work on a bunch of games, and the more readily available the code is, the faster we can prototype them).

Of course, prioritizing what functionalities are coded first is a key component to getting things done quickly … but … if I have a brain storm idea and I want to script it out, i can do so without worrying about when or how i’ll use it …

Thanks.

The biggest boosts that I’ve seen come from:

a) not doing too much in each frame. for example, if you need to spawn 10 new enemies, spawn them over the next 10 frames instead of all at once. amortize the cost.

b) move things out of Update that don’t need to be there. if something can be in FixedUpdate and still do what you need it to do, that’ll be a win for performance.

Yeah … so far, from my review of the documentation … the two key event handlers are Update and FixedUpdate.

Update being called with every frame, and FixedUpdate being called a set number of times per second (or something – physics updates).

I really can’t wait to get to work on some scripting … I’ve been doing quite a bit with GarageGame’s Torque Game Builder over the past year and have contributed quite a bit back to the community, hoping to be able to do the same here – Community seems quite friendly, extremely helpful and unbelievably quick on the draw when it comes to replying to forum posts.

I should be getting my iMac sometime early this week (Apple had issues shipping it on time, gah, haha). So, expect more questions later this week … :slight_smile:

You’ve got that the wrong way around. FixedUpdate fires more frequently than Update, so moving things from Update to FixedUpdate will make them more expensive.

That depends on your framerate and what you’ve got the physics timestep set to. If you’re typically getting 100fps and the fixed timestep is .02 (60fps), then Update is more frequent. In any case, moving stuff between Update and FixedUpdate isn’t going to make any appreciable difference most of the time.

–Eric

Good point. My frame rate is usually slower than my fixed timestep. :wink:

Well, it’s probably something that shouldn’t be relied on for performance reasons anyway. FixedUpdate is intended for use with objects that are using the physics engine, so anything you do with them in FixedUpdate is in sync with the physics, which it wouldn’t be if you’re using Update. And conversely, of course, anything you do in FixedUpdate for non-physics objects won’t be in sync with the framerate, which in some cases can make things look slightly jittery.

Generally I think it’s a good idea to move stuff out of Update or FixedUpdate altogether unless it’s something you really need to check every frame. Instead of incrementing a timer and checking that every frame, for example, use InvokeRepeating or yield WaitForSeconds if you can. Instead of making some conditional variables and checking against them every frame, use a loop with a yield statement. You get more control that way anyway, and your code for a certain condition only runs for as long as you need it. I find that sometimes I don’t use Update at all much except for polling input devices.

It any case, it seems that graphics (shaders, objects, particles, polygons) often slows things down long before scripting does, so it makes more sense for performance reasons to concentrate on keeping the graphics sensible and not worry too much about the scripting.

–Eric

This is not a good idea. Others have said that it depends on what you have set the fixed update rate to, but there is more to it.

The lower your framerate is, the bigger the performance penality you get from FixedUpdate! This is exactly what you don’t want to happen when the purpose is optimizing for speed. When the performance drops, you want to spend less time doing stuff not more.

FixedUpdate is for making things work robust even when frame rate is low thus delta time high and for working with physics. It is not a good utility for making code run faster. yield WaitForSeconds on the other hand can be useful for that purpose, since it lets you wait out dynamic timesteps and also makes sure never to be called twice during the same graphics frame.

Interesting … I’ll keep these things in mind.

For the “yield WaitForSeconds” stuff, would I just start the loop in an Awake or similar event (possibly even a mouse or input event) and then just have the loop run infinitely and use a condition to break out of the loop …

private bool _breakSomeLoop = false;
void someLoop()
{
  while(1)
  {
    // some logic
    if(_breakSomeLoop) break;
    yield 1; 
  }
}

void SomeEventHandler()
{
  someLoop();
}

void SomeOtherEventHandler()
{
  _breakSomeLoop = true;
}

Of course, with a much cleaner design approach, but the rough idea … ? This would then allow the code to only ‘fire’ at a set interval, rather then at a frame or physics update, correct?

Basically, yes. Here’s a bit of code I did for an object that, when instantiated, rolls around for a minimum of 10-15 seconds. Then it waits until it’s come to a stop (if it hasn’t already), and then gets rid of the collider and rigidbody, so it’s not affected by physics or other objects anymore. And then slowly over the course of 10 seconds it sinks down 1 unit on the Y axis (out of sight), and is eliminated.

function Start() {
	yield WaitForSeconds(Random.Range(10.0, 15.0) );
	while (!rigidbody.IsSleeping) {
		yield;
	}
	Destroy(gameObject.collider);
	Destroy(gameObject.rigidbody);
	var originalPosition = transform.position.y;
	for (i = 0.0; i < 10.0; i += Time.deltaTime) {
		transform.position.y = Mathf.Lerp(originalPosition, originalPosition-1, i/10.0);
		yield;
	}
	Destroy(gameObject);
}

So, in this case I didn’t need anything more than a Start function and it’s easy to script the order of events.

–Eric

Eric, – nice, thanks for the script snippet …

Eric, that example would be an excellent example in the Tips and Tricks section of the Wiki :slight_smile: