0

I'm writing a Ray Tracer in C#. I use a Vector3 class for my points, normals, directions and colors. This class is instantiated numerous times per pixel. Is there a way I could structure my code as to avoid the massive amount of garbage collection I am seeing?

Herbstein
  • 309
  • 4
  • 12
  • 1
    It is a struct, not a class, so hard to guess how they ended up in the GC heap. Also very hard to guess how they could survive a gen#0 collection. A blind guess is that you create large arrays of them, re-use them. – Hans Passant Jul 24 '16 at 16:33
  • As long as you have a handle to the memory the garbage collection won't clean it up. Why do you want to avoid GC? are you writing unsafe code? – noone392 Jul 24 '16 at 16:38
  • @Hans: OP probably wrote his/her own `Vector` class. Making it a `struct` would fix the issue, if that is *really* the issue s/he is having. – vgru Jul 24 '16 at 17:09
  • @Herbstein: If you wrote your own `Vector3` class, rewrite it to an immutable `struct`. The *immutable* part is especially important. – vgru Jul 24 '16 at 17:11
  • @Groo I feel stupid now. That was obviously the right thing to do. I'm saving huge amounts of processing time previously spend on GC. This has increased performance massively on my, admittedly, very slow renderer. – Herbstein Jul 24 '16 at 17:56
  • @HansPassant I'm know sure what you are talking about, since all code in my project is made by me. – Herbstein Jul 24 '16 at 17:57

2 Answers2

1

To anyone who finds this through the magic of Google. What I did was changing my Vector3 class to a Vector3 struct. This not only removed the massive GC overhead, but increased performance noticeable.

Herbstein
  • 309
  • 4
  • 12
  • Note that using value types has it's tradeoffs. First, you must understand their semantics and how they differ from reference types. If you're moving these objects frequently, you incur a copy of them each time. Other than that, using them as a value in a collection (`List` as an example) will cause their allocation on the heap. – Yuval Itzchakov Jul 24 '16 at 18:05
  • @YuvalItzchakov: if OP is using floats (i.e. 3 x 32 bits, or 12 bytes), then the difference between passing a 64bit reference (or 8B, presuming a x64 machine) isn't large. When you also consider that a [minimal object size in x64 .NET is 24B](http://stackoverflow.com/questions/10655829/what-is-the-memory-overhead-of-a-net-object), i.e. the object would take twice the memory + additional 64 bits for the reference, then the `struct` becomes even more appealing. *And* you spare the CPU from collecting. If it's an immutable struct, semantics should stay the same (compared to an immutable class). – vgru Jul 24 '16 at 21:25
  • 1
    @Groo I did not mean that a struct isn't more appealing in this particular case. I was just reminding that all this shiny appealing goodness has it's downsides as well for future reference. This post is lacking the information to make any formal statement regarding the efficiency of using structs IMO – Yuval Itzchakov Jul 25 '16 at 04:10
-1

You can use Object Pool pattern to store and reuse your entities. But i am not sure how big would be overhead in boxing/unboxing (if you use value types)

Anton
  • 339
  • 2
  • 15
  • 1
    Value types don't have to be collected, so there isn't much point in using an object pool for them. Even if you did want to do such a thing, you would likely use generic collections, so there wouldn't be any boxing either. – vgru Jul 24 '16 at 17:08