簡體   English   中英

為什么-ffast-math選項打破了我的布爾條件

[英]why -ffast-math option break my bool condition

這是導致問題的程序的關鍵部分,並且程序是完全順序的。

exist_bool類的私有成員,而dbl_num_是class double私有成員

exist_ = false;
dbl_num_ = 0;
std::cout << dbl_num_ << " " ;
if(exist_ == true)
{
  dbl_num_ = 5;
}else
{
  dbl_num_ = NAN;
}

std::cout << exist_ << " " << dbl_num_ << std::endl;

使用選項-ffast-math,我得到打印輸出“ 0 0 5”

沒有選項-ffast-math,我得到打印輸出“ 0 0 NAN”

此外,如果我將程序更改為

exist_ = false;
dbl_num_ = 0;
std::cout << dbl_num_ << " " ;
if(exist_ == true)
{
  std::cout << exist_ << " " ;
  dbl_num_ = 5;
}else
{
  dbl_num_ = NAN;
}

std::cout << exist_ << " " << dbl_num_ << std::endl;

使用選項-ffast-math,我得到“ 0 0 NAN”

比起將NAN改為-5

exist_ = false;
dbl_num_ = 0;
std::cout << dbl_num_ << " " ;
if(exist_ == true)
{
  dbl_num_ = 5;
}else
{
  dbl_num_ = -5;
}

std::cout << exist_ << " " << dbl_num_ << std::endl;

使用選項-ffast-math,我得到“ 0 0 -5”

我知道-ffast-math違反了IEEE標准,並且不檢查NAN,但是究竟是什么原因破壞了上述簡單的條件檢查呢?

-ffast-math指示g ++假定NaN永遠不會發生。 因此,將某些內容設置為NaN大致等同於未定義的行為,因為編譯器可以放心地假設它永遠不會發生。 請參閱這一系列LLVM博客文章,以獲取有關編譯器如何消除其“知道”無法執行的分支的信息,以及如何使之出乎意料。

簡短的版本:g ++變為“我們處於快速數學模式,因此dbl_num_永遠不會設置為NaN,因此永遠不會使用else分支,因此exist_必須為true,因此我可以優化除該路徑以外的所有內容”。

編輯:另請參閱 gcc錯誤報告。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

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