我用
g++ -Wuninitialized
(g++版本7.5.0)编译了以下代码,但没有收到任何警告:
#include <algorithm>
int main() {
int a, b;
b = std::min(a, 0);
}
如您所见,使用参数
std::min()
和 a
调用 0
,但此时 a
尚未初始化。这应该给你一个警告,但事实并非如此。
如果你用自定义函数替换
std::min()
,编译器会给你一个警告:
代码
int f(int x) {
return 2 * x;
}
int main() {
int a, b;
b = f(a);
}
警告
<source>: In function 'int main()':
<source>:11:10: warning: 'a' is used uninitialized in this function [-Wuninitialized]
11 | b = f(a);
| ~^~~
为什么这不适用于
std::min()
?我也尝试过std::max()
,它也没有给我警告。但通过 std::hypot()
我得到了一个。有没有办法让它也适用于std::min()
?
问题在于
std::min
通过引用获取其参数,因此在调用站点 GCC 没有看到未初始化变量的“读取”。由于某种原因,当函数被优化和内联时,它甚至没有注意到未初始化的读取。
如果您将自定义函数更改为
int f(const int& x)
,那么也不会出现任何警告。
这似乎已通过修复Bug 10138在 GCC 11 中得到修复。如果您将未初始化的变量传递给采用
const T&
或 const T*
的函数,GCC 现在会发出警告,这是有道理的,因为这样的函数几乎肯定会计划读取变量,而不是写入变量(这需要强制转换) 。如果它打算读取它,那么它需要被初始化,所以编译器现在会发出警告。