c++局部作用域减少内存

C++ local scopes to reduce memory?

本文关键字:内存 作用域 局部 c++      更新时间:2023-10-16

当尝试尽可能减少内存使用时,我看到一些程序使用额外的本地作用域。这是减少足迹的最好方法吗?当括号关闭时,变量会从堆栈中删除吗?显式地对对象进行delete是更好,还是同样好?或者编译器会直接删除多余的括号吗?

void foo()
{
    {
        int a = 4;
        BigObject obj1;
        obj1.operations(a);
    }
    {
        double b = 9;
        BigObject obj2;
        obj2.operations(b);
    }
}

是的,它们引入了新的作用域。具有自动存储持续时间的对象,即堆栈上的对象("局部变量"),将在此作用域结束时退出作用域。

可以保证析构函数被调用,但不能保证对象实际上从堆栈中删除(因为堆栈是一个实现细节——标准只讨论自动存储持续时间)。然而,这样做很少有性能方面的原因。相反,它在使用RAII模式时很有用。

但是请注意,这只适用于局部变量。动态分配的内存,即堆上的对象(您使用new分配),将不释放,直到您显式地delete它们。

动态分配的内存必须由指针指向。c++明确区分了pointer to BigObjectBigObject的概念。换句话说,您的程序是病态的。你应该写:

BigObject* obj1 = new BigObject();
//       ^-- Important!

你不能用自动存储delete变量,所以你的问题的一部分没有意义。

并不是说你应该用std::unique_ptr来代替new:

std::unique_ptr<BigObject> obj1 = make_unique<BigObject>();

BigObject分配的内存将在obj1超出作用域时自动释放——这是RAII模式。

我过去一直在思考这个问题,但根据我讨厌的实验,现实是它实际上并没有节省空间。局部变量似乎仍然连续地存储在堆栈上:

int _tmain(int argc, _TCHAR* argv[])
{
    int* nasty = NULL;
    {
        int value = 1;
        std::cout << &value << std::endl;
    }
    {
        int value2 = 2;
        std::cout << &value2 << std::endl;
    }
    {
        int value3 = 3;
        std::cout << &value3 << std::endl;
        nasty = &value3;
    }
    std::cout << nasty[0] << ", " << nasty[3] << ", " << nasty[6] << std::endl;
    return 0;
}
输出:

001FFC38
001FFC2C
001FFC20
3, 2, 1