在C ++中意外创建临时对象的方法?

时间:2010-02-08 14:17:20

标签: c++ object temporary

多年前,我相信C与C ++相比绝对纯净,因为编译器无法生成任何您无法预测的代码。我现在相信反例包括volatile关键字和内存障碍(在多处理器编程或内存映射硬件设备的设备驱动程序中,其中普通汇编语言甚至比C编译器的优化更纯粹)。

目前我正在尝试枚举C ++编译器可以执行的不可预测的事情。关于C ++的主要抱怨是编译器将隐式实例化临时对象,但我相信这些情况都可以预期。我正在考虑的案例是:

  • 当一个类为自己以外的类型定义复制构造函数时,不使用explicit关键字
  • 当类定义重载转换运算符时:operator ()
  • 当函数按值而不是按引用
  • 接受对象时
  • 当函数按值而不是按引用
  • 返回对象时

还有其他人吗?

3 个答案:

答案 0 :(得分:2)

我认为“不可预测”意味着“符合标准的东西,但与程序员编写代码时的期望不同”,对吗?

我猜你可以从代码中看到实例化或复制对象的内容,即使它可能并不明显。但可能很难理解。

某些东西只是由(所有?)编译器供应商以某种方式实现,但它可以以不同方式完成。例如,后期绑定(也称为调用重载的虚拟方法)通常使用后台的函数指针来实现。这可能是最快的方式,但我想它可以以不同的方式完成,这将是意想不到的。我不知道任何编译器,但它的表现不同。

在C ++过于复杂的意义上,很多东西都是出乎意料的 - 几乎没有人能理解完整的语言。所以意外也取决于你的知识。

答案 1 :(得分:2)

  

12.2临时对象

     

1班级类型的临时工   在各种上下文中创建:绑定   引用的右值(8.5.3),   返回右值(6.6.3),a   转换,创建一个右值   (4.1,5.2.9,5.2.11,5.4),抛出一个   异常(15.1),进入处理程序   (15.3),并在一些初始化中   (8.5)。

     

4有两种情况   临时的人被摧毁了   不同点比结束了   fullexpression。

事实上我建议看看整个12.2

  

目前我正在努力枚举   不可预测的事情是C ++   编译器可以做。主诉   在我脑海中坚持C ++的是   编译器将隐式地   实例化临时对象,但我   相信这些案件都可以   预期

编译器不会隐式创建临时文件 - 它遵循标准。当然,除非您调用未定义的行为。请注意,有一种称为复制省略和返回值优化的东西,实际上可能会减少原本会被创建的临时数量。

答案 2 :(得分:0)

有关此主题的常见陷阱的有趣链接:

http://www.gotw.ca/gotw/002.htm