有没有办法找到分配给地图的内存大小?

时间:2012-07-18 08:20:30

标签: c++ dictionary

有没有找到在c ++中分配给地图的内存量/大小的方法? 有一个函数可以找到地图的大小,即地图中的条目数,但是存在任何这种方法。 我有一个地图(字符串,字符串)。 sizeof()总是给我48的大小。这是什么原因? 谢谢:))

5 个答案:

答案 0 :(得分:4)

没有简单的方式,但如果你真的必须知道(虽然......为什么会这样?),那么你可以找到答案。

默认情况下,所有标准库容器都使用“默认分配器”进行分配,这只是一个结构/类,在newdelete周围有一对包装函数(它们本身就是内部的) ,只是在mallocfree周围的包装器,在许多编译器上有一点对齐和类型转换。)

如果您因任何原因对默认分配器不满意,可以为容器模板提供自定义分配器,它将无缝地使用该分配器。

如果你编写一个在分配/解除分配时递增/递减整数的分配器,你知道已经动态分配了多少内存。再加上sizeof的值非常精确。

答案 1 :(得分:2)

不,没有。但是,您可以为支持.size方法的类(如字符串或标准容器)实现类似的功能:

template <class Key, class Value>
unsigned long mapSize(const std::map<Key,Value> &map){
    unsigned long size = sizeof(map);
    for(typename std::map<Key,Value>::const_iterator it = map.begin(); it != map.end(); ++it){
        size += it->first.size();
        size += it->second.size();
    }
    return size;
}

如果您想知道分配的内存,可以使用.capacity

template <class Key, class Value>
unsigned long mapCapacity(const std::map<Key,Value> &map){
    unsigned long cap = sizeof(map);
    for(typename std::map<Key,Value>::const_iterator it = map.begin(); it != map.end(); ++it){
        cap += it->first.capacity();
        cap += it->second.capacity();
    }
    return cap;
}

答案 2 :(得分:1)

映射类的大小为48.映射的实例将在堆栈中创建,我们插入的任何记录都将存储在堆中。因此map对象将只指向堆中的记录。怀疑可能就像为什么即使在插入记录后它为48。由于记录不与地图对象一起存储,因此大小是恒定的 - 48.如答案中所述,对象大小在运行时间内不会发生变化。

map =

使用的总大小
((sizeof(key)+sizeof(value))* map.size())+sizeof(map)

map.size()将给出地图中的记录数

48是地图实例的大小。

答案 3 :(得分:0)

对象在运行时无法更改其大小。对于地图,与大多数std容器一样,内存是动态分配的。要查找地图占据并管理的总大小,您可以执行以下操作:

std::map<X,Y> mymap;
int totalSize = sizeof(mymap);
int noElements = 0;

for ( std::map<X,Y>::iterator i = mymap.begin() ; i != mymap.end() ; i++ )
   noElements++;

totalSize += noElements * sizeof(X);
totalSize += noElements * sizeof(Y);

答案 4 :(得分:0)

由于google将我引到了这里,所以无论如何我都会发布一些较晚的答案-因为接受的答案无法回答问题。

这是我所做的(沿着Damon建议的内容),这取决于malloc的实现。在glibc / linux上,返回指针后面的位置给出了分配的大小,因此,可以使用以下代码来跟踪分配/取消分配的字节:

#define HEAP_TRACE

#include <new>

static size_t                             heap_trace_allocated_bytes            = 0;
static size_t                             heap_trace_deallocated_bytes          = 0;
static size_t                             heap_trace_allocated_bytes_baseline   = 0;
static size_t                             heap_trace_deallocated_bytes_baseline = 0;

void* operator new(std::size_t size) {
    void* alloc_entry = std::malloc(size);
    if (!alloc_entry) {
        throw std::bad_alloc();
    }
    heap_trace_allocated_bytes += *(size_t*)(((size_t)alloc_entry)-sizeof(size_t));
    //std::cout << "(-1) equals " << size << " : " << *(size_t*)(((size_t)alloc_entry)-sizeof(size_t)) << std::endl << std::flush;
    return alloc_entry;
}

void operator delete(void* alloc_entry) noexcept {
    heap_trace_deallocated_bytes += *(size_t*)(((size_t)alloc_entry)-sizeof(size_t));
    //std::cout << "(-1) : " << *(size_t*)(((size_t)alloc_entry)-sizeof(size_t)) << std::endl << std::flush;
    std::free(alloc_entry);
}

void setHeapTraceBaseline() {
    heap_trace_allocated_bytes_baseline   = heap_trace_allocated_bytes;
    heap_trace_deallocated_bytes_baseline = heap_trace_deallocated_bytes;
}

void getHeapTraceInfo(string title) {
    std::cout << "\t" << title << ":" << std::endl;
    std::cout << "\t\tAllocations:   " << (heap_trace_allocated_bytes   - heap_trace_allocated_bytes_baseline)   << " bytes" << std::endl;
    std::cout << "\t\tDeallocations: " << (heap_trace_deallocated_bytes - heap_trace_deallocated_bytes_baseline) << " bytes" << std::endl;
    std::cout << std::endl << std::flush;
}

,用法如下:

setHeapTraceBaseline();
// your algorithms
getHeapTraceInfo("My Algorithm allocation costs");

希望这对某人有帮助。

注意:这不是用于生产,因为我的新产品不是可重入的。我在多线程单元测试中成功运行了它。