oli*_*ver 6 c++ floating-point warnings clang gcc-warning
如果我将编译器选项-Wfloat-equal与 GCC 或 Clang 一起使用,浮点/双精度值的相等比较会导致警告。但是,当比较float 或 double 值的容器(如std::vector或std::tuple)时,不会引发此类警告。
示例代码(也在https://godbolt.org/z/YP8v8hTs3):
#include <tuple>
#include <vector>
#include <assert.h>
int main() {
double d = 1.2;
std::tuple<double, double> t_d{1.2, 3.14};
std::tuple<double, double> t_d_2{1.2, 3.14};
std::vector<double> v_d{1.2, 3.14};
std::vector<double> v_d_2{1.2, 3.14};
// this causes a warning, like "warning: comparing floating-point with '==' or '!=' is unsafe [-Wfloat-equal]":
assert(d == 1.2);
// but why no warning from -Wfloat-equal here?
assert(t_d == t_d_2);
// no warning here either:
assert(v_d == v_d_2);
// all of these cause warnings as expected:
assert(std::get<0>(t_d) == 1.2);
assert(std::get<0>(t_d) == std::get<0>(t_d_2));
assert(v_d[0] == 1.2);
assert(v_d[0] == v_d_2[0]);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
为什么这些容器比较中省略了警告?更重要的是,我该怎么做才能真正收到这些警告?
默认情况下, GCC不报告系统标头的警告。可以通过添加编译器标志来获得所需的行为-Wsystem-header。
文档中的引用:
-Wsystem-headers打印系统头文件中发现的构造的警告消息。来自系统头的警告通常会被抑制,假设它们通常不指示真正的问题,只会使编译器输出更难以阅读。使用此命令行选项告诉 GCC 从系统标头发出警告,就像它们发生在用户代码中一样......
现场演示: https: //godbolt.org/z/s6rExszj6
Clang似乎采用了相同的方法,请参阅https://clang.llvm.org/docs/UsersManual.html#controlling-diagnostics-in-system-headers和https://clang.llvm.org/docs/UsersManual.html#控制错误和警告消息的选项。
现场演示:https://godbolt.org/z/n9xY8rcM8