5

Possible Duplicate:
Structure Vs Class in C#

Sorry if this is a open ended question, but I just want to know if my struct is too big. The reason why i want to use a struct is because I've learned that they're faster then classes and I really need the speed, I think.

I found out that if your struct is too big it actually slows down your program, so I want to know whats the guideline on this and whether or not my struct needs to be converted to a class or not.

public struct Tiles
{
    public Rectangle rect;

//i know this wont run with them being initalized like this but if i change to a class this will 
//stay like this and im in the middle of deciding what to do

    Bitmap currentPic = new Bitmap(50, 50);
    ImageAttributes imgAttr = new ImageAttributes();
    float[][] ptsArray;
    ColorMatrix clrMatrix;

    public void setTiles(int i, int k, int width, int height)
    {
        Rectangle temp = new Rectangle(i, k, width, height);
        rect = temp;

        float[][] ptsTemp ={
         new float[] {1, 0, 0, 0, 0},
         new float[] {0, 1, 0, 0, 0},
         new float[] {0, 0, 1, 0, 0},
         new float[] {0, 0, 0, .9f, 0},
         new float[] {0, 0, 0, 0, 1}};

        ptsArray = ptsTemp;
        clrMatrix = new ColorMatrix(ptsArray);
        currentPic = The_Great_Find__Dig_Deeper.Properties.Resources.darknessflashlight;
    }

    public void setTransperancy(float value)
    {
        clrMatrix.Matrix33 = value;
    }

    public void drawRect(Graphics g)
    {
        imgAttr.SetColorMatrix(clrMatrix, ColorMatrixFlag.Default, ColorAdjustType.Bitmap);

        g.DrawImage(currentPic, rect, 0, 0, currentPic.Width, currentPic.Height, GraphicsUnit.Pixel, imgAttr);
    }

    bool blackened
    {
        get;
        set;
    }
}

Should I change it to a class? It's getting kinda bloated to me. I'm using Visual Studio 2008.

Community
  • 1
  • 1
Bigfatty
  • 159
  • 4
  • 10
  • 2
    It doesn't look bloated. It looks messy. The indentation is messy. And in Visual Studio, you can use Ctrl+K+D to fix that. – BoltClock May 03 '11 at 00:09
  • 15
    There's no magic to structs that makes them universally faster than classes. There are many situations where they will be slower. structs can also really surprise you if you don't understand how they work. Generally speaking, I'd recommend sticking with a class. – Matt Greer May 03 '11 at 00:09
  • guess ill chang it to a class then. sorry for the duplicate subject. – Bigfatty May 03 '11 at 00:21
  • 2
    Use a profiling tool to measure your performance and then optimize based on facts rather than guesses. You'll never get good performance by guessing wildly like you're doing now. – Eric Lippert May 03 '11 at 07:19
  • I would suggest that any fields within the struct which hold references to mutable classes should be readonly, and should be instantiated to hold new object instances (though nothing would prevent one from using a default constructor to create a struct with those fields blank, the only way to create a valid struct would be to use a constructor that would initialize those fields). – supercat Oct 06 '11 at 16:26

4 Answers4

8

Advice to non-blackbelt programmers: don't optimise your code.

Advice to blackbelt programmers: optimise your code later.

I seriously recommend you heed this advice!

To give you some more pertinent explanation, you should be aware that, unlike classes, structs are allocated on the stack, not on the heap. Stack allocation is slightly cheaper, but is usually only appropriate for small, objects that are either short-lived or which are passed by value or which are going to be stored in a large array.

If you don't know what passed by value means, it means that the entire struct is copied whenever you pass it as an argument to a method. This can quickly become very expensive if your structs are not very small. It can also lead to unexpected behaviour if you don't understand this distinction: changes made to a class argument in a method are visible to the method caller; changes made to a struct argument in a method are not visible to the method caller (because the method is changing a copy of the original data).

To reiterate my first point: don't use structs unless you're sure you know what you're doing.

Hope this helps!

Rafe
  • 5,237
  • 3
  • 23
  • 26
  • This actually helped alot. Thanks for breaking it down for me. – Bigfatty May 03 '11 at 00:25
  • 9
    `structs are allocated on the stack, not the heap` - This is a common error. The allocation behavior in the CLR for value types (structs) is far more complicated. Please read: http://stackoverflow.com/questions/4853213/c-struct-stack-allocated-or-sometimes-heap-allocated/4853251#4853251 – LBushkin May 03 '11 at 00:32
  • 5
    The whole idea that the *kind* of a thing determines where it is allocated is nonsense on the face of it. Clearly whether a thing is allocated on the short-lifetime store (the stack) or the long-lifetime store (the heap) depends on it's *lifetime*, not whether the storage is copied by value or by reference! – Eric Lippert May 03 '11 at 07:16
  • @Eric Lippert, Fair enough. I think, to a good first order approximation, structs *can be reasonably said* to be allocated on the stack. I understood the OP was looking for a "useful" answer rather than a discussion of possible optimisations the compiler might carry out. – Rafe May 04 '11 at 07:09
  • 6
    **Structs cannot reasonably be said to be allocated on the stack**. Structs that are static fields, instance fields, closed-over locals of an anonymous function, locals of an iterator block or inside an array are not allocated on the stack. Structs that are optimized into registers are not allocated on the stack. And everyone forgets about references! The *referant* of a reference is never on the stack, but the *reference* is frequently on the stack. Why does everyone always forget about references? They can take up huge amounts of stack. Or registers. – Eric Lippert May 04 '11 at 16:13
  • 5
    Furthermore, your contention that stack allocation is "cheaper" seems suspect. Why should allocation by moving the stack pointer be any more or less expensive than allocation by moving the top of the GC heap pointer? The expense isn't the *heap allocation*; the expense is the side effect of the heap allocation which is *collection pressure* that leads to more frequent garbage collections. – Eric Lippert May 04 '11 at 16:16
  • @Eric Lippert, stack allocation is cheaper because (a) it can't lead to a GC and (b) you don't migrate stack objects during a collection. Would you have been happier if I'd said words to the effect that stack allocated objects incur less memory management overheads? For what it's worth, I agree with you from the outset that it's the *passing semantics* that are important; perhaps I should have mentioned that first. – Rafe May 05 '11 at 03:26
  • Stack allocation is much cheaper, because the top of the stack is typically hot in the cache, while freshly allocated heap memory is often cold and writing to it causes a cache miss. – Piotr Kołaczkowski Jan 31 '20 at 16:56
3

Size isn't the reason to choose a struct over a class. Use struct ONLY if you want value semantics. Think about an int; 5 is a 5 is a 5, references don't matter. structs are always passed by making a copy.

Use a struct when you want value semantics. Otherwise, use a class.

Andy
  • 8,432
  • 6
  • 38
  • 76
2

Preemptive optimization is the root of all evil. Or so the saying goes. Build your application, and only then, if it has performance problems try to fix them. For example, one method may run twice as slow as another method, but you can parallize the first and run 4 at a time. Therefore the first method is actually faster. You have to fully understand your performance problem before you can fix it.

To answer your question: From what I recall a struct of size 16 bytes or larger is slower than a class when passed to a method.

Charles Lambert
  • 5,042
  • 26
  • 47
  • 16 bytes it is: http://msdn.microsoft.com/en-us/library/ah19swz4(v=vs.71).aspx – Liviu Trifoi May 03 '11 at 00:32
  • 1
    All this time i would usually always try to think of the most efficent way to go about programming something and then do it, but now i guess ill just programm it, and if necessary optimize it later. thx for the advice. – Bigfatty May 03 '11 at 00:39
1

Could you please define "speed"?

If the program runs in 10 sec using classes and the same program takes 9.4 sec using structs does it speed up the program or is it a conceivable speed?

You also have to remember that copying will be longer for struct compared to a reference type.

You are the one who can exactly determine if a Struct or Class serves your purpose.

Use Struct if

  1. Object is Small.
  2. Logically immutable.

If I were you I would rather use a profiler to exactly know where exactly the program is running slow.

As far as I know, you can not achieve a conceivable improvement using struct instead of class.

Sandeep
  • 7,156
  • 12
  • 45
  • 57