C # optimization - arrays / lists of value types and stack (games)

I am working on a game, and I am in the middle of a few AI, and I want to optimize the code as much as I can. I have several structures in my code like Circle, Vector, etc. I want to minimize the load on the GC as a result of this code, since it will work many times per second, and in each call several large arrays will be created and a lot of calculations will be done.

My question is: if I have a small method that can "return" several types of values โ€‹โ€‹(that is, the intersection of a circle and a vector, etc.), what is the most efficient way to pass its result back to the main method?

I can come up with several ways to do this:

  • Returns an array of results ie Vector []
  • Returns a list of <Vector>
  • Pass to list <Vector>
  • Any other way.?

What would be the best strategy to avoid the large number of small unnecessary objects / arrays on the heap that the GC needs to collect?

+4
source share
3 answers

If you are in a situation where:

  • You often call this method.
  • You will always be dealing with the same collection size (or similar, at least)
  • You do not need previous results at the time of the next call

... then you can improve performance by repeatedly moving into the same array (or List<T> ) and modifying it. On the other hand, you must absolutely measure your performance before making any changes. You must also determine what will be โ€œgood enoughโ€ so that you do not bend your code from the most natural design more than you need.

+7
source

It depends on what type of data was transmitted; in most cases, games use vector structures, intersection data, etc.

When data is a structure, you should avoid List<T> and pass on each value because the data is copied. But it depends a lot on the code, sometimes passing for a value can be faster, sometimes not. I would do some performance tests. You can use this method for simple tests without a profiler:

 public static Int64 MeasureTime(Action myAction) { var stopWatch = new Stopwatch(); stopWatch.Start(); myAction(); stopWatch.Stop(); return stopWatch.ElapsedMilliseconds; } 

When working with structures, you can always use out or ref .

Additional Information

All these situations may not cause performance problems, they simply explain the best practices that I learned when working with structures. To determine if ref and out are useful in each case, you should run a performance test.

ref used to prevent such situations:

 Vector input = new Vector(x, y, z); input = ModifyVector(input); // This line causes copies of the input vector and it slow 

The performance that falls here depends on the size of the Vector class, but it is not recommended to use the following method each time. When returning a simple Int32, it is not needed and should not be used to read code.

The right way:

 Vector input = new Vector(x, y, z); ModifyVector(ref input); 

Of course, the ref keyword can be used to speed up methods that return nothing, but these methods should take care of the data passed to them and avoid modifying them. In some situations, the speed advantage may be more than 50% (I have a high-performance vector library, and I checked many cases).

out used to prevent such situations:

 Ray ray = ...; CollisionData data = CastRay(ref ray); // Note the ref here to pass the Ray which contains 6 floats 

CollisionData contains at least the point where it hits the ground and normal. When using out here to get the result, it should be much faster.

The right way:

 Ray ray = ...; CollisionData data; CastRay(ref ray, out data); 

When using arrays.

.. you should know that the array is already a reference, and you do not need the ref or out keyword to process them. But when working with structures, you should know that you do not keep references to structures in your array. Therefore, by changing the value of the array, you can use ref myArray[0] to pass the value to the method and change the structure with a zero index without copying it. Also avoid creating new instances.

+2
source

I donโ€™t know what platform / infrastructure you have (XNA?), But I ran into a problem with GC under Windows Phone 7 (7.5 got GC of generating generation, but did not test it). To avoid the so-called GC freezes, I made a collection where I preloaded all the necessary data into the dictionary.

but the first measure is the measure of the measure.

0
source

Source: https://habr.com/ru/post/1393660/


All Articles