临时保管人的存储期限有什么要求?
What's the requirement for storage duration of temporaries?
考虑以下代码:
class Test() {
public:
Test()
{
memset( buffer, 0, sizeof( buffer ) );
}
void Process()
{
printf( buffer );
}
private:
char buffer[1000];
};
int main()
{
Test().Process();
char buffer[1000] = {};
print( buffer );
return 0;
}
我不能推断出main中的buffer
是否允许重用之前被class Test
的临时对象占用的内存。根据标准自动存储(3.7.2/1)必须至少持续到块结束。
我找不到强制临时对象使用自动存储的措辞,除了6.6/2,其中描述了一个跳转语句,并说在退出作用域时[…],对于所有具有自动存储持续时间(3.7.2)的构造对象(命名对象或临时对象)调用析构函数(12.4),这似乎暗示临时对象使用自动存储。
临时需要使用自动存储吗?在main
的局部变量在上面的代码允许重用内存以前占用的临时或它应该使用不同的存储?
临时对象的生存期(除非绑定到const&
)延伸到完整表达式的末尾。在您的情况下,main
中的第一行。编译器允许重用相同的内存,但是否这样做是一个实现细节(即实现质量)
12.2 (class.temporary)
/3[…临时对象在求值的最后一步被销毁(词法上)包含创建点的完整表达式(1.9)。[…]
/4在两种上下文中,临时变量在与完整表达式末尾不同的位置被销毁。第一个上下文是当表达式作为定义对象的声明符的初始化项出现时。[…]
/5第二个上下文是当引用被绑定到临时对象时。
由于您不属于任何例外,因此Test
临时属于第一类,并且作为第一行求值的最后一步被销毁。
3.7.2/1特别讨论了块作用域变量。它们的存储空间必须持续整个块。然而,正如您所发现的,临时变量确实具有自动存储持续时间,但不是块范围变量。
语法Test()
创建一个临时。这与命名为:
Test iHaveAName;
一个命名对象有块持续时间;它会一直持续到街区结束。临时具有表达期限;当它所在的表达式结束时,它将被销毁。
因此,如果您执行Test().Process()
, Test()
临时将存在足够长的时间,以便Process()
完成。
Test
实例一直存在到;
实例存在为止。未指定buffer
是否重用Test
实例使用的存储。据我所述,标准中没有任何内容阻止编译器重用该空间。
这是实现定义的。智能编译器可以通过对齐堆栈指针来优化代码,以便buffer
可以重用内存。
- 为不同配置设置MSVC_RUNTIME_LIBRARY的正确方法是什么
- 警告处理为错误这里有什么问题
- 什么时候调用组成单元对象的析构函数
- #定义c-预处理器常量..我做错了什么
- 努力将整数转换为链表。不知道我在这里做错了什么
- C++我的数学有什么问题,为什么我的代码不能正确循环
- 什么时候在C++中返回常量引用是个好主意
- 当在同一名称空间中有两个具有相同签名的函数时,会发生什么
- C++避免重复声明的语法是什么
- c++库的公共头文件中应该包含什么
- 问题:什么是QAbstractItemView::NoEditTriggers的反面
- 有什么方法可以遍历结构吗
- 当类在C++中定义时,有什么方法可以"register"类吗?
- ifstream什么都没读
- 在C++中,将大的无符号浮点数四舍五入为整数的最佳方法是什么
- 实现无开销push_back的最佳方法是什么
- C++从另一个类访问公共静态向量的正确方法是什么
- "throw expression code" 1e7 >返回 d 是什么?投掷标准::overflow_error( "too big" ) : d;意味 着?
- 我应该使用什么来代替void作为变体中的替代类型之一
- 临时保管人的存储期限有什么要求?