Xeo*_*Xeo 18 c++ offsetof undefined-behavior
来自MSVC实施的示例:
#define offsetof(s,m) \
(size_t)&reinterpret_cast<const volatile char&>((((s *)0)->m))
// ^^^^^^^^^^^
Run Code Online (Sandbox Code Playgroud)
可以看出,它取消引用空指针,通常会调用未定义的行为.这是规则的例外还是正在发生的事情?
Che*_*Alf 25
在语言标准说"未定义的行为"的地方,任何给定的编译器都可以定义行为.标准库中的实现代码通常依赖于此.所以有两个问题:
(1)代码UB是否与C++标准有关?
这是一个非常难的问题,因为它是一个众所周知的几乎缺陷,C++ 98/03标准从未在规范性文本中说明,一般来说,取消引用nullpointer是UB.它暗示由例外typeid,在那里它不 UB.
你可以肯定地说,它是UB offsetof与非POD类型一起使用.
(2)代码UB是针对编写的编译器吗?
不,当然不.
编译器供应商的给定编译器代码可以使用该编译器的任何功能.
干杯&hth.,
AnT*_*AnT 15
"未定义行为"的概念不适用于标准库的实现,无论它是宏,函数还是其他任何东西.
一般情况下,不应将标准库视为以C++(或C)语言实现.这也适用于标准头文件.标准库应符合其外部规范,但其他所有内容都是实现细节,不受语言的所有和任何其他要求的约束.标准库应始终被认为是以某种"内部"语言实现的,这种语言可能非常类似于C++或C,但仍然不是C++或C.
换句话说,您引用的宏不会产生未定义的行为,只要它特别offsetof是标准库中定义的宏.但是如果你在代码中做了完全相同的事情(比如以相同的方式定义自己的宏),它确实会导致未定义的行为."Quod licet Jovi,non licet bovi".