[英]Is a standards conforming C++ compiler allowed to optimize away branching on <= 0 for unsigned integers?
考慮以下代碼:
void foo(size_t value)
{
if (value > 0) { ... } // A
if (value <= 0) { ... } // B
}
由於無符號不能為負,符合C ++編譯器的標准是否可以優化B語句? 或者它只是選擇比較0?
好吧,它顯然無法完全消除B語句 - 條件體在value
0時執行。
由於value
無論如何都不能< 0
,編譯器當然可以將B轉換為if (value == 0) { ... }
。 此外,如果它可以證明(記住標准要求嚴格的別名規則!)該value
不會被語句A改變,它可以合法地轉換整個函數,如下所示:
void foo(size_t value)
{
if (value > 0) { ... } // A
else { ... } // B
}
或者,如果碰巧知道目標架構喜歡==
更好,那么:
void foo(size_t value)
{
if (value == 0) { ... } // B
else { ... } // A
}
如果代碼被正確寫入,則B
不能被優化掉,因為value
可以為零,盡管使用的特定比較可以用等效的替換,如Angew的答案所示。 但是如果B
的語句調用未定義的行為,那么所有的賭注都會被取消。 為了便於參考,讓我們重寫foo
為
void foo(size_t value)
{
if (value > 0) bar(); // A
if (value <= 0) baz(); // B
}
如果編譯器可以確定baz()
調用未定義的行為,那么它可以將其視為無法訪問。 從那以后,它可以推導出該value > 0
,並優化foo
void foo(size_t value)
{
bar();
}
由於如果unsinged value == 0
,必須執行復合語句,因此符合標准的編譯器無法優化if (value <= 0) { /* ... */ }
。
優化編譯器可能會考慮以下幾點:
value
不能小於零 這種情況有幾種可能的“結果”,其中每種情況都包含一個比較和一個條件跳轉指令。
我懷疑test R,R
比cmp R, 0
更“優化” cmp R, 0
但總的來說沒有太大區別。
生成的代碼可以是(代碼A和代碼B包含ret):
使用cmp
cmp <value>, 0
一種)
je equal
// Code A
equal:
// Code B
B)
jne nequal
// Code B
nequal:
// Code A
C)
jg great
// Code B
great:
// Code A
d)
jbe smoe
// Code A
smoe:
// Code B
使用test
test <value>, <value>
一種)
je equal
// Code A
equal:
// Code B
B)
jne nequal
// Code B
nequal:
// Code A
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.