2010-07-23 12 views
12

aşağıdaki birim testi düşünün:Neden Guid.ToString ("n") aynı kılavuzun bir bayt dizisinden oluşturulmuş bir hex dizesiyle aynı değil?

[TestMethod] 
    public void TestByteToString() 
    { 
     var guid = new Guid("61772f3ae5de5f4a8577eb1003c5c054"); 
     var guidString = guid.ToString("n"); 
     var byteString = ToHexString(guid.ToByteArray()); 

     Assert.AreEqual(guidString, byteString); 
    } 

    private String ToHexString(Byte[] bytes) 
    { 
     var hex = new StringBuilder(bytes.Length * 2); 
     foreach(var b in bytes) 
     { 
      hex.AppendFormat("{0:x2}", b); 
     } 
     return hex.ToString(); 
    } 

İşte sonuç var:

Assert.AreEqual failed. Expected:<61772f3ae5de5f4a8577eb1003c5c054>. Actual:<3a2f7761dee54a5f8577eb1003c5c054>.

cevap

11

Eh, onlar ilk 4 bayt sonra aynıdır. Ve ilk dört aynıdır, sadece ters sırada.

Temel olarak, dizeden oluşturulduğunda, "büyük-endian" biçiminde olduğu varsayılır: Soldaki en yüksek bayt. Ancak, dahili olarak saklandığında (Intel-ish makinesinde), baytlar “küçük-endian” olarak adlandırılır: sağdaki en yüksek bayt. Eğer sonuçları karşılaştırırsanız

12

, ilk üç grup tersine görebilirsiniz:

GUID structure yılında, bu 3 grup DWORD ve iki WORD s ziyade bayt olarak tanımlanır çünkü var
 
61 77 2f 3a e5 de 5f 4a 8577eb1003c5c054 
3a 2f 77 61 de e5 4a 5f 8577eb1003c5c054 

:

{0x00000000,0x0000,0x0000,{0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}} 

bellekte Intel işlemcisi bunları küçük-endian düzeninde (en son en son bayt) saklar. aşağıdaki gibi

4

Bir GUID yapılandırılmıştır:

int a 
short b 
short c 
byte[8] d 

Yani a tarafından temsil bölümü için kod bayt tersine alır. Diğer tüm parçalar doğru şekilde dönüştürülür.

+1

Neden "b" ve "c" de tersine çevrilmeyecek? – Sebastian

+0

@SebastianGodelet - çünkü "int" yerine "kısa" dırlar. – ChrisF

+1

Bir bayttan daha büyük olan her şeyin endianna tabi olduğunu düşündüm: 'short s = 0xaf21;' saklanabilir: | af | 21 | veya | 21 | af | – Sebastian