Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/153.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 为什么VC++;2010允许编译这个吗? std::vector vci; vci.推回(1); vci[0]=2;_C++_Visual C++ - Fatal编程技术网

C++ 为什么VC++;2010允许编译这个吗? std::vector vci; vci.推回(1); vci[0]=2;

C++ 为什么VC++;2010允许编译这个吗? std::vector vci; vci.推回(1); vci[0]=2;,c++,visual-c++,C++,Visual C++,当元素类型为const int时,赋值语句不应该赋值给const int&?这不会使用LLVM 3.0编译。为什么VC++允许它?虽然它是未定义的行为,基本上任何事情都可能发生,包括您看到的,但我一直在跟踪这一点,直到库与标准不兼容为止。特别是VS2010库中定义的标准分配器不符合该标准 该标准规定,std::vector::value_type是对Allocator::value_type的类型定义。现在默认的分配器(如果没有提供)是std::allocator,根据表28,其value\u

当元素类型为
const int
时,赋值语句不应该赋值给
const int&
?这不会使用LLVM 3.0编译。为什么VC++允许它?

虽然它是未定义的行为,基本上任何事情都可能发生,包括您看到的,但我一直在跟踪这一点,直到库与标准不兼容为止。特别是VS2010库中定义的标准分配器不符合该标准

该标准规定,
std::vector::value_type
是对
Allocator::value_type
的类型定义。现在默认的分配器(如果没有提供)是
std::allocator
,根据表28,其
value\u type
必须与T相同。现在VS2010中标准分配器的实现从type参数中删除
const
限定符,因此
std::allocator::value\u type
T
,而不是
const T

需要注意的是,编译器对于接受您提供的代码本身并不是不一致的,因为它是未定义的行为,并且编译器可以随意执行。但另一方面,
std::allocator
实现中存在不一致性


你自己已经回答了这个问题:这是未定义的行为。编译器不需要提供诊断,操作的结果可以是任何东西。检测类型不可分配并提供有意义的错误消息(或不可分配)是实现质量的一个例子。

您显然不理解“未定义的行为”中“未定义的”一词的含义。奉承会让您无处不在——我本可以用更好的措辞。对不起,我不是有意冒犯您,但通常未定义的行为被误认为是运行时崩溃或编译错误保证。没有比这更离谱的了。C++中有很多地方,其中有些看似合理的东西确实是被禁止的,但编译器不负责检查。未定义的行为意味着不要这样做。。。这意味着编译器编写者可以自由地假设程序员不会这样做。可能发生的最糟糕的事情就是“什么都没有”。。。不过,在
std::vector
的任何实际实现中,都会有某个地方试图进行赋值,这将导致一个彻底的编译器错误。事实上,这并没有发生,这让它很有趣;MSVC实现有什么诀窍?这怎么可能是一个QoI问题?如何在不分配给
const
的情况下实现这一点?UB似乎使用了不可分配的UDT,但使用
常量
类型却违反了语言规则,不是吗?@Tabber33:如果差异仅在已经是未定义行为的代码中才可察觉,这样它就不会影响代码与标准的一致性,它就变成了QoI。@Tabber33:在追逐代码和标准之后,只有
const
被删除,它发生在
std::allocator
中,这使得分配器的实现与标准中的表28不一致(这要求
value\u type
与T相同)。看起来它实际上是不一致的,不是因为
const
被删除了,而是因为它在
std::allocator
中被删除了)@Tabber33:
const\u cast
从对象而不是从类型中删除了常量。对于类型,这是可以对类型进行的最简单的元编程:
template struct remove_const{typedef T type;};模板结构删除_const{typedef T type;}(在本例中,这是分配器的基础,
类型
实际上是
值类型
,但方法是相同的。
std::vector<const int> vci;
vci.push_back(1);
vci[0] = 2;