Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/138.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 为什么我的自定义堆栈类使用了这么多内存?_C++_Memory Management_Stack - Fatal编程技术网

C++ 为什么我的自定义堆栈类使用了这么多内存?

C++ 为什么我的自定义堆栈类使用了这么多内存?,c++,memory-management,stack,C++,Memory Management,Stack,我在单链表的基础上制作了自己的堆栈,它工作得很好,但是当我 查看了内存使用情况。。。 使用包含100k整数的堆栈的控制台应用程序占用了6.5MB。这很糟糕,因为4字节*100k=0.38MB。我为每个“单元”结构分配内存,其中一个包含指向下一个的指针,但我认为这不会占用很多内存。问题的原因是什么 template <typename T> class Stack { struct Unit { Unit *prev; T val

我在单链表的基础上制作了自己的堆栈,它工作得很好,但是当我 查看了内存使用情况。。。 使用包含100k整数的堆栈的控制台应用程序占用了6.5MB。这很糟糕,因为4字节*100k=0.38MB。我为每个“单元”结构分配内存,其中一个包含指向下一个的指针,但我认为这不会占用很多内存。问题的原因是什么

template <typename T>
class Stack
{
        struct Unit
    {
        Unit *prev;
        T value;
        Unit(T value);
    };
public:
    Stack();
    void Push(T value);
    int Count();
    T Top();
    T Pop();
    ~Stack();
private:
    unsigned int count;
    Unit *top;

};

template<typename T>
Stack<T>::Unit::Unit(T value)
{
    this->value = value;
    prev = nullptr;
}

template<typename T>
Stack<T>::Stack()
{
    top = nullptr;
    count = 0;
}

template<typename T>
void Stack<T>::Push(T value)
{
    if (top == nullptr)
    {
        top = new Unit(value);
    }
    else
    {
        Unit *tmp = new Unit(value);
        tmp->prev = top;
        top = tmp;
    }
    count++;
}

template<typename T>
T Stack<T>::Pop()
{
    T value = top->value;
    Unit *tmp = top->prev;
    delete top;
    top = tmp;
    count--;
    return value;
}

template<typename T>
Stack<T>::~Stack()
{
    Unit *curr = top;
    if (!curr)
    {
        return;
    }
    while (curr)
    {
        Unit* tmp = curr->prev;
        delete curr;
        curr = tmp;
    }
}
模板
类堆栈
{
结构单元
{
单位*prev;
T值;
单位(T值);
};
公众:
堆栈();
空隙推力(T值);
int Count();
T-Top();
T Pop();
~Stack();
私人:
无符号整数计数;
单位*顶部;
};
模板
堆栈::单位::单位(T值)
{
这个->值=值;
prev=nullptr;
}
模板
Stack::Stack()
{
top=nullptr;
计数=0;
}
模板
无效堆栈::推送(T值)
{
if(top==nullptr)
{
top=新单位(值);
}
其他的
{
单位*tmp=新单位(值);
tmp->prev=顶部;
top=tmp;
}
计数++;
}
模板
T Stack::Pop()
{
T值=顶部->值;
单位*tmp=top->prev;
删除顶部;
top=tmp;
计数--;
返回值;
}
模板
堆栈::~Stack()
{
单位*电流=顶部;
如果(!curr)
{
返回;
}
while(curr)
{
单位*tmp=curr->prev;
删除curr;
curr=tmp;
}
}

在计算大小时,没有考虑指针的大小和结构的任何填充。在您的平台上,指针可能是4或8个字节。此处讨论填充:

我在构造器中为堆栈添加了一个cout,以显示结构单元的大小:

#include <iostream>
template<typename T>
Stack<T>::Stack()
{
    top = nullptr;
    count = 0;

    std::cout << "The size of each unit is "  << sizeof(Unit) << " bytes." << std::endl;
} 

// Rest of code is copied directly from the question.

int main() {

    Stack<int> myStack;

    return 0;
}
完整示例如下:

编辑:

在看到提出问题的人正在使用VisualStudio之后,我进行了一些额外的调试以了解情况。在调试模式下,调试运行时向每个分配添加额外的空间,以允许堆损坏检测和堆跟踪。我在main结束之前设置了一个断点,并查看了TaskManager中的内存使用情况(是的,这不是最准确的度量)。在调试模式下,整个应用程序使用了超过12MB的内存,而在发布模式下,总内存使用量为2.6MB

每个区块的额外分配信息如下:

堆函数的调试版本调用标准或基函数 发布版本中使用的版本。当您请求内存块时 调试堆管理器从基本堆中分配稍大的 内存块,并返回指向该部分的指针 从那个街区出去。例如,假设您的应用程序包含 电话:malloc(10)。在发布版本中,malloc将调用base 请求分配10字节的堆分配例程。在一个 然而,调试构建时,malloc将调用_malloc_dbg,然后 调用基本堆分配例程,请求分配10 字节加上大约36字节的额外内存。所有的 调试堆中产生的内存块以单个内存块连接 链表,根据分配时间排序


使用包含100k整数的堆栈的控制台应用程序占用了6.5MB。这很糟糕,因为4字节*100k=0.38MB。您没有计算指针的大小。这应该是4或8个字节。您的结构也可能有填充。打印(单元)的
sizeof
以查看每个
Unit
占用的空间。您如何测量内存?你知道6.5MB中有多少是典型的开销吗?当你完成实验时,只需使用你基本上有一个链表。下面是我在第一条评论中提到的一个例子:
The size of each unit is 16 bytes.