C++ 传递整数文本时是否没有隐式转换警告?

C++ 传递整数文本时是否没有隐式转换警告?,c++,implicit-conversion,C++,Implicit Conversion,我试图了解隐式转换何时发生,并检测它们以提高代码库的质量 我已为此启用了Wconversion和Wsign转换。然而,我遇到了一个编译器没有给出任何错误的情况。例如: #include <iostream> #include <array> int main() { std::array<int, 10> vec{}; std::cout << vec[1] << std::endl; } 数组的大小和运算符[]的索引

我试图了解隐式转换何时发生,并检测它们以提高代码库的质量

我已为此启用了
Wconversion
Wsign转换。然而,我遇到了一个编译器没有给出任何错误的情况。例如:

#include <iostream>
#include <array>

int main()
{
   std::array<int, 10> vec{};
   std::cout << vec[1] << std::endl; 
}
数组的大小和
运算符[]
的索引应为
std::size\t
类型(无符号)。然而,我正在传递有符号的文本,似乎没有问题。我甚至可以将
1.0F
传递给
操作符[]
,编译器就可以了

但是,如果我为
运算符[]
的索引创建了一个有符号变量,那么编译器会警告隐式转换

引擎盖下发生了什么?使用文字时是否发生隐式转换?为什么编译器不给出一个错误?我在Ubuntu18.04上使用GCC 7.4。

警告“将有符号转换为无符号”存在,因为其中一些转换可能会产生糟糕/意外的结果。将有符号的
1
转换为无符号的
1
不会产生任何问题。将
-3
转换为未签名是有问题的


对于变量,编译器(在一般情况下)无法知道其在运行时的值,因此必须警告潜在的转换问题。对于文本,它的值在编译时是已知的,因此编译器可以静默地执行正确的操作(当值转换为OK时),或者在必要时发出警告/出错(当转换有问题时)。

编译器不会发出警告,因为它在编译时知道此转换是否安全,即。,原始值和目标值相同。当您这样做时:

vec[1.0F]
从编译器的角度来看,
1.0F
1
之间的值没有变化(精度损失),因此编译器不会警告您。如果您尝试:

vec[1.2F]
…编译器将警告您,因为即使
1.2F
将转换为
1
,也会丢失精度

如果使用编译时未知的值,例如:

float get_float();

vec[get_float()];
您将收到预期的警告,因为编译器事先不知道
get\u float()
的值,因此无法确保转换是安全的


请注意,当需要常量表达式时(例如,在
std::array
中),您永远不会收到此类警告,因为根据定义,常量表达式在编译时是已知的,因此,编译器知道给定值和转换值之间是否存在问题。

您不会收到警告,因为编译器在编译时知道这些转换是正常的,如果您在编译时使用一些不知道的内容,您将收到预期的警告。我明白了,谢谢!这个行为是由标准保证的还是依赖于编译器的?我想知道,如果某些编译器在这里有一个奇怪的行为,是否最好保护自己并显式地使用“例如数组[0U]”。例如,当运行静态分析(MISRA C++ 2008 5-0 4)@ USE1011113时,PCLLT对此抱怨,您不能保证对此类代码发出警告,因为警告没有被标准强加。您可以确定的是,
array[0]
必须在任何编译器上编译,即使有些编译器可能发出警告。我个人会使用
array[0]
,因为我看不出显式的好处,但这是一个选择的问题。
float get_float();

vec[get_float()];