post your code.
I did a collision detection engine where the static mesh are created at load time, and shouldn't incur any game time pressures to the GC.
You probably got a ref object in there somewhere that you think is a value object
Well there is just way too much code to post it (and I don't really think this is the correct thread for it). I am sure I am not allocating ref objects during the game loop as I have carefully stepped through it looking for exactly that. The more likely
cause is that I am using the .Net or XNA classes in such a way that garbage is created that I am unaware of. This is a minefield where innocent "mistakes" lead to garbage. Examples of things that could create garbage during the game loop:
- Calling anonymous methods or closures.
- Setting/clearing delegates or event handlers.
- Using an enum as a key in a dictionary. Simply doing a lookup creates garbage in this case.
- Doing "silly" things like wanting to create strings using "+" or "string.Format, etc.
- Adding/removing items out of a LinkedList. It is very common to have objects added/removed from linked lists in the game loop. So now you have to roll your own linked list, or use something other than linked lists.
- Accessing value types
via an interface will cause them to be boxed (was not aware of this).
- Some enumerators create garbage. Good luck figuring out which ones do and which ones don't. Quick: Does foreach() on a Dictionary ValuePair create garbage? Often it seems safer just to fall back to for() if you are unsure (where the collection allows this).
- Using yield in order to enumerate objects.
- And who-knows-what-else happens behind the scene as you use the built-in .Net classes.
The point is, you might not create garbage while using your own classes/structs, but there are many cases where simply doing things that look innocent causes garbage to be created.
This is a
quote from Shawn Hargraves (works on XNA Game Studio at MS):
You can achieve good performance by avoiding allocations, so the garbage collector will never run. This works regardless of how complex your heap may be.
You can also achieve good performance by keeping your heap nice and simple, so the garbage collector will finish quickly. This works regardless of whether you allocate memory during gameplay.
But you cannot achieve good performance by mixing these two approaches! There is little to be gained by allocating only a medium amount of memory and having only a medium complex heap. That will produce a game which has a medium size glitch every
medium number of seconds.
If your goal is to avoid garbage collection glitches altogether, you must pick just one path and follow it to the bitter end.
This just isn't ideal. An incremental GC would help since then you don't need to worry about creating some amount of garbage (within reason) at each frame, no matter how large your object graph is. Having to pick between one of the two above approaches and then
ensuring that you stick to it really complicates things. Java has an optional low-pause incremental collector, why not .Net?
EDIT: @Charles: Sorry, only saw your post after I posted. Will stop posting now. If someone wants to discuss the details further, we can create another thread.