• Create Account

Slowdowns / 'Anti-Hotspot'

Old topic!

Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.

8 replies to this topic

#1Imprecision  Members

194
Like
0Likes
Like

Posted 25 September 2012 - 11:46 AM

Hi,

I'm working on my Quad-Tree for a while now, to generate the landcape. I optimized it pretty nicely so its able to produce new quads in 1 - 2ms.
The problem is that C# slows down when there wasn't create a new quad for a while (while means starting from 500ms).
Here an example:

Node gen; total 106ms noise 69 vert 11 rest
Node gen; total 2ms noise 1 vert 0 rest 1
Node gen; total 2ms noise 0 vert 0 rest 1
Node gen; total 2ms noise 0 vert 0 rest 1
Node gen; total 3ms noise 0 vert 0 rest 2
Node gen; total 4ms noise 2 vert 0 rest 1
Node gen; total 7ms noise 1 vert 0 rest 6
Node gen; total 4ms noise 2 vert 0 rest 2
Node gen; total 37ms noise 1 vert 0 rest 35
Node gen; total 3ms noise 1 vert 0 rest 1
Node gen; total 19ms noise 17 vert 0 rest 1
Node gen; total 18ms noise 17 vert 0 rest 1
Node gen; total 19ms noise 17 vert 0 rest 1
Node gen; total 19ms noise 17 vert 0 rest 1
Node gen; total 2ms noise 1 vert 0 rest 1
Node gen; total 2ms noise 1 vert 0 rest 1
Node gen; total 22ms noise 16 vert 0 rest 4
Node gen; total 2ms noise 1 vert 0 rest 1
Node gen; total 18ms noise 17 vert 0 rest 1
Node gen; total 19ms noise 17 vert 0 rest 1
Node gen; total 19ms noise 17 vert 0 rest 1
Node gen; total 18ms noise 15 vert 0 rest 2
Node gen; total 19ms noise 17 vert 0 rest 1
Node gen; total 18ms noise 17 vert 0 rest 1
Node gen; total 2ms noise 1 vert 0 rest 1
Node gen; total 18ms noise 16 vert 0 rest 1
Node gen; total 2ms noise 1 vert 0 rest 1
Node gen; total 19ms noise 17 vert 0 rest 1
Node gen; total 2ms noise 0 vert 0 rest 1
Node gen; total 2ms noise 1 vert 0 rest 1

As you can see the time for the generation CAN be very fast, but it slows down for no reason
The difficulty of the data to create dosen't change at all.

I know that C# / .NET optimizes parts of code that are 'in heavy use'like the hotspot technology in JVM.
Is there any way to enable it manually? How do you handle it?

#2Telastyn  Members

3773
Like
0Likes
Like

Posted 25 September 2012 - 02:52 PM

As you can see the time for the generation CAN be very fast, but it slows down for no reason

There's always a reason. For C#, that reason is usually the garbage collector.

3482
Like
0Likes
Like

Posted 25 September 2012 - 05:21 PM

What you need to diagnose the issues is a profiler.

#4Imprecision  Members

194
Like
0Likes
Like

Posted 29 September 2012 - 08:12 AM

There's always a reason. For C#, that reason is usually the garbage collector.

Can I avoid this problem by creating nodes in a new thread?

What you need to diagnose the issues is a profiler.

Mh... I don't think this is what I need. It's not that I don't understand which parts of code lines are slow, I don't know why the are getting slow by random.

#5kd7tck  Members

735
Like
0Likes
Like

Posted 29 September 2012 - 02:06 PM

There's always a reason. For C#, that reason is usually the garbage collector.

Can I avoid this problem by creating nodes in a new thread?

What you need to diagnose the issues is a profiler.

Mh... I don't think this is what I need. It's not that I don't understand which parts of code lines are slow, I don't know why the are getting slow by random.

This is not random. There is a reason for it, probably a lack of memory.

The profiler will tell you if you have enough memory or not.

#6Telastyn  Members

3773
Like
0Likes
Like

Posted 29 September 2012 - 07:30 PM

Can I avoid this problem by creating nodes in a new thread?

No.

Another idea is that the resolution of your timer isn't fine enough to measure the true duration of your work. The large difference depends then on if you happen to catch the timer on the outward or inward swing

#7zalzane  Members

191
Like
0Likes
Like

Posted 02 October 2012 - 11:41 AM

Quadtrees tend to be very computationally expensive, and even worse - tend to do lots of heap allocations in loops. I couldn't tell you without looking at your code, but it may be possible that the problem is the garbage collector. If you wanted to stay using c#, you may be able call the GC class and have it clean up after every node is created.

It's unusual that the garbage collector would block you that badly unless you were doing LOTS of heap allocations that keep the variables alive for periods of time where the garbage collector can't figure out if it should treat the variables as a short-lifespan object or a long-lifespan object.

#8PhillipHamlyn  Members

564
Like
0Likes
Like

Posted 05 October 2012 - 01:56 AM

I you're using generics (i.e. List<Node>) or any other kind of List inside your QuadTree and adding one node at a time, it is very well worth creating your list with a initial size like this;

List<Node> nodes = new List<Node>(32) rather than use the default of "1". As the list extends .net will double the memory allocation for it each time it reaches the end of its preallocated buffer limit - which takes time. If you initialize it to a reasonable guesstimate of the likely size, .net will allocate the memory once-only during class initialization without the need to allocation incrementally with the attendant memory fragmentation. Of course, you dont want to guess too big, because the memory is actually allocated.

I wouldn't recommend touching the GC at all - it does the job its supposed to do. Many people recommend GC.Collect "to make .net faster" but its often an error; the real problem is in the excessive allocation and reallocation of objects and the fragementation that leads from it. For instance; always consider using a for(int) loop rather than a foreach() within quadtree parsing - foreach() creates and destroys and enumerator object - expensive in the kind of nested looping common in quadtrees, whereas the old fashioned for(int) doesn't.

As recommended by the other posters - you reallly, really need to use a profiler. VS.net has one built in, otherwise Ants is a very good one.

#9frob  Moderators

41398
Like
0Likes
Like

Posted 05 October 2012 - 08:53 AM

I wouldn't recommend touching the GC at all - it does the job its supposed to do. Many people recommend GC.Collect "to make .net faster" but its often an error; the real problem is in the excessive allocation and reallocation of objects and the fragementation that leads from it. For instance; always consider using a for(int) loop rather than a foreach() within quadtree parsing - foreach() creates and destroys and enumerator object - expensive in the kind of nested looping common in quadtrees, whereas the old fashioned for(int) doesn't.

As recommended by the other posters - you reallly, really need to use a profiler. VS.net has one built in, otherwise Ants is a very good one.

This is especially true in games.

Here in our studio we use C# for multiple titles. We never need to force garbage collection to run.

Almost certainly you are creating unnecessary objects and either leaving them in use or casually throwing them away. That is an area that C++ at least forces you to deal with so you realize when you are doing it, C# makes it very easy to create many unnecessary objects consuming your memory in horrible ways.

When performance suddenly slows, we can usually track it down to a programmer spewing out temporary objects or using weak references. A few moments on the profiler will find the source of these allocations rather quickly.

Check out my book, Game Development with Unity, aimed at beginners who want to build fun games fast.

Also check out my personal website at bryanwagstaff.com, where I occasionally write about assorted stuff.

Old topic!

Guest, the last post of this topic is over 60 days old and at this point you may not reply in this topic. If you wish to continue this conversation start a new topic.