Bu hack'i anlamak için, önce işaretçi farkını anlamalısınız, yani, aynı dizinin öğelerini işaret eden iki işaretçi çıkarıldığında ne olur ?
Bir işaretçi diğerinden çıkarıldığında, sonuç işaretçiler arasındaki mesafedir (dizi öğelerinde ölçülür). Yani, eğer p
işaret eder a[i]
ve q
işaret ederse a[j]
, o p - q
zaman eşittiri - j
.
C11: 6.5.6 Katkı operatörleri (s9):
İki işaretçi çıkarıldığında , her ikisi de aynı dizi nesnesinin öğelerini veya dizi nesnesinin son öğesinin ötesini işaret eder; sonuç, iki dizi öğesinin aboneliklerinin farkıdır . [...].
Başka bir deyişle, ifadeler P
ve Q
sırasıyla bir dizi nesnesinin i
-th ve j
-th öğelerini gösteriyorsa , ifadenin (P)-(Q)
, değerini−j
türdeki bir nesneye uyması koşuluyla değeri olur ptrdiff_t
.
Şimdi işaretçi için dizi adı dönüşüm farkında olduğunuzu umuyorum, a
işaretçi dizinin ilk öğesine dönüştürür a
. &a
tüm bellek bloğunun adresidir, yani bir dizi adresidir a
. Aşağıdaki şekil anlamanıza yardımcı olacaktır ( ayrıntılı açıklama için bu cevabı okuyun ):
Bu, neden a
ve &a
aynı adrese ve (&a)[i]
i th dizisinin adresinin (adresiyle aynı boyutta a
) nasıl olduğunu anlamanıza yardımcı olacaktır .
Yani, açıklama
return (&a)[n] - a;
eşittir
return (&a)[n] - (&a)[0];
ve bu fark işaretçiler arasındaki (&a)[n]
ve her bir elemanın dizisi (&a)[0]
olan elemanların sayısını verecektir . Bu nedenle, toplam dizi elemanları = 2'dir . n
n
int
n*n
n
NOT:
C11: 6.5.6 Katkı operatörleri (s9):
İki işaretçi çıkarıldığında, her ikisi de aynı dizi nesnesinin öğelerini veya dizi nesnesinin son öğesinin ötesini işaret eder ; sonuç, iki dizi öğesinin aboneliklerinin farkıdır. Sonucun boyutu uygulama tanımlıdır ve türü (işaretli bir tamsayı türü) başlıkta ptrdiff_t
tanımlanır <stddef.h>
. Sonuç bu tür bir nesnede gösterilemiyorsa, davranış tanımsızdır.
Bu yana (&a)[n]
bir dizi objenin son öğe geçen aynı dizi nesne veya bir elemanlarına de nokta, (&a)[n] - a
açılmasına neden olur tanımsız davranış .
Ayrıca işlevin dönüş türünü değiştirmek için daha iyi, dikkat p
etmek ptrdiff_t
.