Интересные заметки по C# и CLR (v2.0)

class MyClass { private string _field1 = «Some string 1»; public string Field2 { get; set; } } IL видим два поля: .field private string 'k__BackingField' .field private string _field1 И два метода: .method public hidebysig specialname instance string get_Field2() cil managed .method public hidebysig specialname instance void set_Field2(string 'value') cil managed Посмотрим кто куда попал: 0:003>! do 0000005400006600 Name: ConsoleApplication1.MyClass MethodTable: 00007ffa2b5c4378 EEClass: 00007ffa2b6d2548 Size: 32(0×20) bytes File: E:\…\ConsoleApplication1.exe Fields: MT Field Offset Type VT Attr Value Name 00007ffa89d60e08 4000002 8 System.String 0 instance 0000005400006620 _field1 00007ffa89d60e08 4000003 10 System.String 0 instance 00000054000035a0 k__BackingField Поля попали прямо к экземпляру, и повлияли на его минимальный размер (32 потому что с 17 по 24 бит заняла первая ссылка (ранее были пустыми), а 25–32 вторая (что бы сохранить порядок их следования есть атрибут). Но методов непосредственно в экземпляре нет, только ссылка на них, и соответственно они не повлияли на его размер.

Посмотрим таблицу методов:

0:003>! dumpmt -md 00007ffa2b5c4378 EEClass: 00007ffa2b6d2548 Module: 00007ffa2b5c2fc8 Name: ConsoleApplication1.MyClass mdToken: 0000000002000003 File: E:\…\ConsoleApplication1.exe BaseSize: 0×20 ComponentSize: 0×0 Slots in VTable: 7 Number of IFaces in IFaceMap: 0 -------------------------------------- MethodDesc Table Entry MethodDesc JIT Name 00007ffa89ae6300 00007ffa896980e8 PreJIT System.Object.ToString () 00007ffa89b2e760 00007ffa896980f0 PreJIT System.Object.Equals (System.Object) 00007ffa89b31ad0 00007ffa89698118 PreJIT System.Object.GetHashCode () 00007ffa89b2eb50 00007ffa89698130 PreJIT System.Object.Finalize () 00007ffa2b6e0390 00007ffa2b5c4358 JIT ConsoleApplication1.MyClass…ctor () 00007ffa2b5cc130 00007ffa2b5c4338 NONE ConsoleApplication1.MyClass.get_Field2() 00007ffa2b5cc138 00007ffa2b5c4348 NONE ConsoleApplication1.MyClass.set_Field2(System.String) А вот и они, оба еще не прошли JIT-компиляцию, кроме конструктора и унаследованных экземплярных методов от System.Object которые Ngen себя при установке .NET.В заключение этого пункта посмотрим полный размер экземпляра с размером объектов на которые указывают его поля:

MyClass mcClass = new MyClass (); mcClass.Field2 = «Some string 2»;

0:003>! objsize 0000005400006600 sizeof (0000005400006600) = 144 (0×90) bytes (ConsoleApplication1.MyClass) Проверим это посмотрев на размер полей: 0:003>! objsize 0000005400006620 sizeof (0000005400006620) = 56 (0×38) bytes (System.String) 0:003>! objsize 00000054000035a0 sizeof (00000054000035a0) = 56 (0×38) bytes (System.String) Итого: 56 + 56 + 32 = 144.

© Habrahabr.ru