2016-03-12 15 views
5

Sizeof operatörünü kullanarak tüm değişkenlerimin büyüklüğünü (değer türleri) kontrol etmeye çalışıyorum. Ben yapılar da dahil olmak üzere tüm diğer türleri içinsizeof operatörü bir yapı içinde ekstra boyut verir C#

, sizeof operatörü sadece güvensiz kod blokları

ve ayrıca yapılar herhangi içermemelidir kullanılabilir yazılıdır msdn article biri aracılığıyla gitmiş alanlar veya referans tipleridir Bunun için

özellikleri, ben AŞAĞIDAKİ

struct EmployeeStruct 
{ 
    int empId; 
    long salary;  
} 
olarak benim proje özelliklerinde güvensiz derleme ve oluşturulan yapıyı etkin 10

ve

unsafe 
{ 
    size = sizeof(EmployeeStruct); 
} 

Console.WriteLine("Size of type in bytes is: {0}", size); 

aşağıdaki- olarak kullandı İşte byte olarak Çeşidi Boyut gibi çıkışını edilir alıyorum: 16 ancak yapının bakarak o 12 (uzun süre int için 4 ve 8) olmalıdır. Birisi bana neden 4 bayt ekstra boyut aldığımı anlamanıza yardımcı olabilir mi?

+0

Verdiğiniz bağlantı size şunları söyler: "sizeof, dilbilgisi çalışma zamanı tarafından tahsis edildiği şekliyle boyutu döndürürken, ** herhangi bir dolgu ** dahil olmak üzere **" – DavidG

+0

@EugenePodskal Çok şey değiştirir - yanıt arayan kişiler C# 'daki bir problem C ile ilgili sorulara bakmaz, cevaplar aynı olsa bile çok farklı dillerdir. –

+0

@GediminasMasaitis Daha sonra bu soruyu bulabilir ve kopyasını okuyacaklar (en azından en azından olmalılar). Ama bu çabaya değer olduğunu düşünüyorsanız, o zaman uygun bir kurallı C# -belirli cevap yazabilirsiniz. Bu durumda, soruyu daha kolay aranabilir ve noktaya "beklenen değerden daha büyük olan geri döndürme değeri" veya bu satırdaki bir şey olarak yeniden adlandırmanızı tavsiye ederim. –

cevap

1

Güvenli olmayan kod kullanmanız gerekmez. System.Runtime.InteropServices.Marshal.SizeOf()

kullanılması önerilir: Marshal.SizeOf (new EmployeeStruct()); bellekte varsayılan paketi boyutu olduğu için için, 8.

Yani, 16 yerine 12 dönmek

:

struct EmployeeStruct 
{ 
    int empId; // 4 bytes 
    long salary; 8 bytes 
} 

// dönmek yerine 16 12 (de dk birimi olduğu için 8)

için:

struct EmployeeStruct 
{ 
    int empId; // 4 bytes 
    int empAge; // 4 bytes 
    long salary; 8 bytes 
    } 

// çok

return

ve

struct EmployeeStruct 
    { 
     int empId; // 4 bytes 
     int empAge; // 4 bytes 
     int IdCompany; // 4 bytes 
     long salary; 8 bytes 
    } 

dönüş 24 yerine 20 (de dk birimi olduğu için 8)

Ne istediğini bilmiyorum ama her alan boyutu toplamını gerekirse şunları yapabilirsiniz için örneğin, O dava için, 12 yerine 16 döndürür

public int SizeOf(Type t) 
    { 
     int s = 0; 
     var fields = t.GetFields(BindingFlags.Public | BindingFlags.Instance | BindingFlags.NonPublic); 
     foreach (var f in fields) 
     { 
      var x = f.FieldType; 
      s += x.IsPrimitive ? Marshal.SizeOf(x) : SizeOf(x); 
     } 

     return s; 
    } 

ve karmaşık yapılar için kullanabilirsiniz: Bu işlevle deneyin

struct EmployeeStruct 
    { 
     int field1; // 4 bytes 
     long field2; // 8 bytes 
     Person p; // 12 bytes 
    } 

    struct Person 
    { 
     int field1; // 4 bytes 
     long field2; // 8 bytes 
    } 

SizeOf (typeof (EmployeeStruct) 32 yerine 24 döndürecektir, ancak unutmayın, BELLEK ÜZERİNE GERÇEK BOYUTU 32, derleyici bellek atamak için 32 bayt kullanır.

Saygılarımızla.

+0

Ama sonra neden üç 'int' ile bir yapı 16 ve 16 değil bir boyutu var? –

+0

Thnx Gonzalo. Ancak, System.Runtime.InteropServices.Marshal.SizeOf, bataklıktan sonra yönetilmeyen ayrılmış boyut döndürdüğü doğru değil mi? Doğru yönetilen veya CLR ayrılmış boyut elde etmek için herhangi bir yolumuz yok mu? –

+0

Cevabımı düzenledim, belki size yardımcı olabilirim. Saygılarımızla. – Gonzalo