有人可以向我解釋爲什麼下面的代碼輸出0 0
。我是數學上a-b == 0
a == b
⇒值相同但不相等
char* V1 = "hello, world!\n";
main(){
F1(V1);
}
F1(A1){
printf("%u %u\n", V1 - A1, V1 == A1);
}
有人可以向我解釋爲什麼下面的代碼輸出0 0
。我是數學上a-b == 0
a == b
⇒值相同但不相等
char* V1 = "hello, world!\n";
main(){
F1(V1);
}
F1(A1){
printf("%u %u\n", V1 - A1, V1 == A1);
}
作爲每C11
標準,章節§6.5.6,兩個指針只能任何只有當它們是從同一陣列對象中減去的印象。
當兩個指針相減,既應指向同一陣列對象, 或一個過去的數組對象的最後一個元素的元素;結果是兩個數組元素的 下標的差異。結果的大小是實現定義的, 及其類型(有符號整數類型)是
<stddef.h>
標頭中定義的ptrdiff_t
。 如果結果在該類型的對象中不可表示,則行爲未定義。 [...]
這就是說,你應該使用%td
打印ptrdiff_t
類型的結果,從指針減法產生。
接下來,使用==
運算符,它不能用來比較字符串(數組)的內容,它基本上比較指針本身(而不是它們指向的內容)。
好吧,所以兩個值不相等的原因是因爲這是未定義的行爲? – user12341234
@ user12341234首先,它是錯誤的代碼(沒有違法),其次,'=='和'strcmp()'不一樣,第三,你是對的。 –
首先:沒有冒犯,我沒有寫這個,只是簡化了它。其次:我不認爲最初的意圖是比較字符串內容,但指針。第三:感謝。 – user12341234
As @SouravGhosh指出,這裏有一個未定義的行爲。儘管如此,理解爲什麼第二個打印值有時是0並且有時是1(取決於它運行的機器),這很有趣。
輸入F
缺少顯式類型意味着A1
隱含爲int
。函數調用F(V1)
因此將指針V1
轉換爲int
。在某些機器上,這可能是一個縮小的轉換,這就是爲什麼在某些機器上比較V1 == A1
是正確的,而在其他機器上是錯誤的。也許在某些機器上,V1 - A1
中的兩個參數都被轉換爲整數(因此值爲0),但是在比較V1 == A1
(這是ub)試圖將A1
轉換爲有效地址並失敗或將其轉換爲不同的地址。
但是,如果值相同,並且縮小了,那麼'=='的兩個操作數都不會被降低並仍然相等? – user12341234
好問題。將整數與指針比較是未定義的行爲,因此比較是未定義的。在任何情況下,'V1 == V1' *爲真,並且'A1 == V1'有時評估爲false,而從'pointer'到'int'的隱式強制轉換是唯一一個兩端之間的差異可以引入比較。也許問題不是縮小本身,而是轉換爲有符號的數字。 –
不要告訴我你真的寫了代碼..... –
這是一個最小的可行的例子,從別人的錯誤代碼...他們聲稱它在Visual Studio中工作正常... – user12341234
'=='比較在C中的字符串並不意味着你認爲它的意思。 – callyalater