none
calculate size of an object in .net

    Question

  • Hi,

    i am trying to calculate memory size of a hashtable which hold about 3000 key value pairs.

    can any one please tell that how i can get it,

    means how much memory this object is consuming.

     

    thanks

     

    Ali

     

    Monday, June 18, 2007 9:47 AM

Answers

  • There is no real way to know how much memory the object is using.  The hashtable itself takes up some space.  Each key will take up additional space (not part of the hashtable) and each value has its own set of space.  If any of these have children then the children are separate as well.

     

    The sizeof keyword in C# can be used to find the size of any value type but requires the use of unsafe code for anything other than PoDs.  The Marshal.SizeOf method can be used to calculate the unmanaged size of an object but it will not handle the various subobjects mentioned earlier.  The only way to determine the actual memory used would be to walk every object and every child object referenced.  An alternative would be to serialize the binary object out to a binary formatter.  This would give you a close approximation of the binary size but not necessarily the actual memory size.

     

    You can use a profiler to get a better idea of the memory usage of an object but you can't do this programmatically very easily.

     

    Michael Taylor - 6/18/07

    http://p3net.mvps.org

    Monday, June 18, 2007 12:42 PM
    Moderator
  • You can't find out directly, you don't have access to the private members of the Hashtable class to find out how many hash buckets were allocated.  3000 x (size of key object + size of value object) is a pretty good approximation.  You can use Marshal.SizeOf() to get the allocation size of a simple object, one that doesn't store references.
    Monday, June 18, 2007 12:46 PM
    Moderator

All replies

  • There is no real way to know how much memory the object is using.  The hashtable itself takes up some space.  Each key will take up additional space (not part of the hashtable) and each value has its own set of space.  If any of these have children then the children are separate as well.

     

    The sizeof keyword in C# can be used to find the size of any value type but requires the use of unsafe code for anything other than PoDs.  The Marshal.SizeOf method can be used to calculate the unmanaged size of an object but it will not handle the various subobjects mentioned earlier.  The only way to determine the actual memory used would be to walk every object and every child object referenced.  An alternative would be to serialize the binary object out to a binary formatter.  This would give you a close approximation of the binary size but not necessarily the actual memory size.

     

    You can use a profiler to get a better idea of the memory usage of an object but you can't do this programmatically very easily.

     

    Michael Taylor - 6/18/07

    http://p3net.mvps.org

    Monday, June 18, 2007 12:42 PM
    Moderator
  • You can't find out directly, you don't have access to the private members of the Hashtable class to find out how many hash buckets were allocated.  3000 x (size of key object + size of value object) is a pretty good approximation.  You can use Marshal.SizeOf() to get the allocation size of a simple object, one that doesn't store references.
    Monday, June 18, 2007 12:46 PM
    Moderator
  • thanks Taylor,

    serlization is a good idea.

    can you name any profiler to me which i can use with .net 2.0

    i downloaded one from gotdotnet.com using this link

    http://www.gotdotnet.com/Community/UserSamples/Details.aspx?SampleGuid=36A3E666-6877-4C26-B62D-BFD7CB3154AC

    but for unknown reasons it is complaining about a dll. the program could not load the dll and throws unable to load dll exception.

    the dll file is in the same folder where the application is.

     

    thank again for ur support

    looking forward

     

    Ali

    Monday, June 18, 2007 4:13 PM
  • I'm not sure whether is this the right way or not. But this is one of the ways. You can find the size if your class the serializable.

        [Serializable]
        public class MyClass
        {
            Byte[] m_aBuffer = new Byte[1000];
        }

            private static void FindSize()
            {
                long lSize = 0;          
                MyClass objMyClass = new MyClass();

                try
                {
                    System.IO.MemoryStream stream = new System.IO.MemoryStream();
                    BinaryFormatter objFormatter = new BinaryFormatter();
                    objFormatter.Serialize(stream, objMyClass);
                    lSize = stream.Length;
          Console.WriteLine("Size of the Object: " + lSize);
                }
                catch(Exception excp)
                {
                    Console.WriteLine("Error: " + excp.Message);
                }

            }
    Monday, August 20, 2007 6:26 AM
  • Hi nobugz,

    What to do when it have some reference in class or struct in Windows Mobile CF

    Then what to do for getting the size of such class or struct which have some refrence to other struct like in the case below.

    [StructLayout(LayoutKind.Sequential)]
        public class ForwardList
        {
            [Internal]
            byte[] m_data;
          
            public ForwardList(int size)
            {
                m_data = new byte[size];
                TotalSize = size;
            }
          
            public byte[] Data { get { return m_data; } }
          
            public int TotalSize
            {
                get { return BitConverter.ToInt32(m_data, 0); }
                set { Buffer.BlockCopy(BitConverter.GetBytes(value), 0, m_data, 0, 4); }
            }       
           
            public int NumEntries
            {
                get { return BitConverter.ToInt32(m_data, 4); }
                set { Buffer.BlockCopy(BitConverter.GetBytes(value), 0, m_data, 4, 4); }
            }       
           
            public LineForward[] List
            {
                get
                {
                    LineForward[] lf = new LineForward[NumEntries];
                    for (int i = 0; i < NumEntries; i++)
                        lf[i] = LineForward.FromByteArray(m_data, Marshal.SizeOf(typeof(LineForward)) * i);
                    return lf;
                }
            }

        }

     

    [StructLayout(LayoutKind.Sequential)]
        public struct LineForward
        {
            public static LineForward FromByteArray(byte[] data, int offset)
            {
                LineForward lf = new LineForward();
                lf.ForwardMode = (ForwardMode)BitConverter.ToInt32(data, offset);
                lf.CallerAddressSize = BitConverter.ToInt32(data, offset + 4);
                lf.CallerAddressOffset = BitConverter.ToInt32(data, offset + 8);
                lf.DestCountryCode = BitConverter.ToInt32(data, offset + 12);
                lf.DestAddressSize = BitConverter.ToInt32(data, offset + 16);
                lf.DestAddressOffset = BitConverter.ToInt32(data, offset + 20);
                return lf;

            }
            public ForwardMode ForwardMode;
            public int CallerAddressSize;
            public int CallerAddressOffset;
            public int DestCountryCode;
            public int DestAddressSize;
            public int DestAddressOffset;

        }

     

    This is what i have done but getting an exception of Notsupportedexception

    int dwSize = Marshal.SizeOf(typeof(ForwardList));

    Help me.

    Thanks in advance

    Monday, May 17, 2010 1:41 PM