5

This question is simply to satisfy my interest. Reading Choosing Between Classes and Structures the page says "It has an instance size smaller than 16 bytes.".

Given this simple immutable struct.

public struct Coordinate
{
    private readonly double _latitude;
    private readonly double _longitude;

    public Coordinate(double latitude, double longitude)
    {
        _latitude = latitude;
        _longitude = longitude;
    }

    public double Latitude
    {
        get { return _latitude; }
    }

    public double Longitude
    {
        get { return _longitude; }
    }
}

Do properties also count towards the 16 byte limit? Or do only fields count?

If the latter wouldn't using a struct fail the guidelines provided by Microsoft since a double is 8 bytes? Two doubles would be 16 bytes which is exactly 16 bytes and not less.

gcso
  • 2,315
  • 3
  • 28
  • 50
  • 1
    possible duplicate of [How to check the number of bytes consumed by my Structure?](http://stackoverflow.com/questions/3361986/how-to-check-the-number-of-bytes-consumed-by-my-structure) – Steve Townsend Jun 29 '11 at 13:12
  • 2
    That guidance is on using whether or not to use a `struct` is somewhat misguided. You should choose whether or not to use a `struct` for semantic reasons. The technical reasons, while okay, should only be minded if you actually find a performance issue from the choice you make for semantic reasons. – jason Jun 29 '11 at 13:21
  • @gcso thanks for the link, interesting read – Lea Hayes Jun 21 '12 at 13:02

4 Answers4

4

Just the fields count.

So in this case you've got two 64-bit (8 byte) fields; you're just about within the bounds of your heuristic.

Note that if you use any auto-implemented properties then the compiler will create "hidden" fields to back those properties, so your overall sum should take those into account too.

For example, this struct also requires 16 bytes:

public struct Coordinate
{
    public Coordinate(double latitude, double longitude) : this()
    {
        Latitude = latitude;
        Longitude = longitude;
    }

    public double Latitude { get; private set; }
    public double Longitude { get; private set; }
}
LukeH
  • 263,068
  • 57
  • 365
  • 409
2

First, to determine the size of your struct, use Marshal.SizeOf(struct) which returns the sum of the sizes of its members. Microsoft does recommend that the size of a struct be below 16 bytes, but it is really up to you. There is some overhead associated with structs. In case your struct has reference types as members, make sure you don't include the size of instances of reference types, just the size of the references.

1

You can find out the size using

System.Runtime.InteropServices.Marshal.SizeOf(new Coordinate());

Which returns 16. You are right - only fields count. You can add properties without increasing the size.

Mark Heath
  • 48,273
  • 29
  • 137
  • 194
  • Does that mean that using 2 `double` properties would fail the Microsoft guidelines since they suggest anything less than 16 bytes? – gcso Jun 29 '11 at 13:16
  • Well strictly it fails their guideline since 16 isn't less than 16. It's an edge case though. Probably depends on how you are planning to use them. – Mark Heath Jun 29 '11 at 13:17
1

You can use sizeof( Coordinate ) to calculate it progamatically, although this will require unsafe context. In your case the size is 16 bytes as you said. Properties do not count towards the size, since they are only wrappers. The size of a structure is simply the sum of the sizes of all its fields.

Georgi Stoyanov
  • 1,208
  • 1
  • 11
  • 13