簡體   English   中英

符合標准的C ++編譯器是否允許在無符號整數上優化<= 0的分支?

[英]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) { /* ... */ }

優化編譯器可能會考慮以下幾點:

  1. 這兩個陳述是互斥的
  2. 它們之間沒有代碼。
  3. value不能小於零

這種情況有幾種可能的“結果”,其中每種情況都包含一個比較和一個條件跳轉指令。

我懷疑test R,Rcmp 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.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM