是的,它在一个尚未构造的对象上调用该函数,这是未定义的行为.你无法检测到它的可靠性.我认为你也不应该试图发现它.与例如在已删除的对象上调用函数相比,这可能是偶然发生的.试图捕捉所有可能的错误几乎是不可能的.声明的名称在其初始化程序中已经可见,用于其他有用的目的.考虑一下:
Type *t = (Type*)malloc(sizeof(*t));
这是C编程中常见的习惯用法,它仍然适用于C++.
就个人而言,我喜欢Herb Sutter关于空引用(同样无效)的故事.要点是,不要试图保护语言明确禁止的情况,特别是在一般情况下不可能可靠地诊断.随着时间的推移,你会得到一个虚假的安全,这变得非常危险.相反,培养您对语言的理解和设计界面(避免原始指针......),以减少出错的可能性.
在C++中,同样在C语言中,许多情况并未明确禁止,而是未定义.部分原因是有些事情很难有效地部分诊断,因为未定义的行为允许实现为它设计替代行为而不是完全忽略它 - 现有编译器经常使用它.
例如,在上述情况下,任何实现都可以自由地抛出异常.还有其他情况同样是未定义的行为,这对于实现来说更难以有效诊断:在构造之前访问不同转换单元中的对象就是这样一个例子 - 这被称为静态初始化顺序fiasco.
是的,它在一个尚未构造的对象上调用该函数,这是未定义的行为.你无法检测到它的可靠性.我认为你也不应该试图发现它.与例如在已删除的对象上调用函数相比,这可能是偶然发生的.试图捕捉所有可能的错误几乎是不可能的.声明的名称在其初始化程序中已经可见,用于其他有用的目的.考虑一下:
Type *t = (Type*)malloc(sizeof(*t));
这是C编程中常见的习惯用法,它仍然适用于C++.
就个人而言,我喜欢Herb Sutter关于空引用(同样无效)的故事.要点是,不要试图保护语言明确禁止的情况,特别是在一般情况下不可能可靠地诊断.随着时间的推移,你会得到一个虚假的安全,这变得非常危险.相反,培养您对语言的理解和设计界面(避免原始指针......),以减少出错的可能性.
在C++中,同样在C语言中,许多情况并未明确禁止,而是未定义.部分原因是有些事情很难有效地部分诊断,因为未定义的行为允许实现为它设计替代行为而不是完全忽略它 - 现有编译器经常使用它.
例如,在上述情况下,任何实现都可以自由地抛出异常.还有其他情况同样是未定义的行为,这对于实现来说更难以有效诊断:在构造之前访问不同转换单元中的对象就是这样一个例子 - 这被称为静态初始化顺序fiasco.