让我们考虑以下代码:
struct Blob {
double x, y, z;
} blob;
char* s = reinterpret_cast<char*>(&blob);
s[2] = 'A';
假设 sizeof(double) 是 8,这段代码会触发未定义的行为吗?
最佳答案
引自 N4140(大致为 C++14):
3.9 Types [basic.types]
2 For any object (other than a base-class subobject) of trivially copyable type
T
, whether or not the object holds a valid value of typeT
, the underlying bytes (1.7) making up the object can be copied into an array ofchar
orunsigned char
.42 If the content of the array ofchar
orunsigned char
is copied back into the object, the object shall subsequently hold its original value.42) By using, for example, the library functions (17.6.1.2)
std::memcpy
orstd::memmove
.3 For any trivially copyable type
T
, if two pointers toT
point to distinctT
objectsobj1
andobj2
, where neitherobj1
norobj2
is a base-class subobject, if the underlying bytes (1.7) making upobj1
are copied intoobj2
,43obj2
shall subsequently hold the same value asobj1
. [ Example: ... ]43) By using, for example, the library functions (17.6.1.2)
std::memcpy
orstd::memmove
.
原则上,如果您认为对 s[2]
的赋值间接要求等同于将所有其他 Blob
复制到一个数组中,该数组恰好除了第三个字节外字节相同,并将其复制到您的 Blob
中:您没有分配给 s[0]
、s[1]
等。对于包括 char
在内的平凡可复制类型,这相当于将它们设置为它们的确切值已经有了,也没有明显的效果。
但是,如果获取 s[2] == 'A'
的唯一方法是通过内存操作,那么也可以提出一个有效的论点,即您正在复制回您的 Blob
不是构成任何先前 Blob
的底层字节。在那种情况下,从技术上讲,行为将因遗漏而未定义。
我强烈怀疑,尤其是考虑到“该对象是否拥有 T
类型的有效值”注释,它是有意被允许的。
关于c++ - 非数组类型的指针算法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34879858/