Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/130.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

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/apache-spark/5.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++ - Fatal编程技术网

C++ 了解堆上保留内存的大小

C++ 了解堆上保留内存的大小,c++,C++,有没有办法获取以前在堆上分配的内存大小? 例如: //pseudo-code void* p = operator new (sizeof(int) * 3); unsigned size = getSomeHow(p); 您不能总是这样做,因为operator new()可以以任何合理的方式重载,甚至可能不使用运行时堆 > 操作符new()/Cuff>在VisualC++中使用MalCube()/实现,您可以使用.< /P>< P>。尽管Sharptooth的答案是正确的(新的可以重

有没有办法获取以前在堆上分配的内存大小?
例如:

//pseudo-code

void* p = operator new (sizeof(int) * 3);
unsigned size = getSomeHow(p);  

您不能总是这样做,因为
operator new()
可以以任何合理的方式重载,甚至可能不使用运行时堆


<> > <代码>操作符new()/Cuff>在VisualC++中使用MalCube()/<代码>实现,您可以使用.< /P>< P>。尽管Sharptooth的答案是正确的(新的可以重载),解决方案可能只是在这个事实中。通过重载new,您可以轻松地添加自己的new和delete实现。在实施新技术的过程中,您应该:

  • 编辑:将大小四舍五入到下一个8字节的倍数
  • 向应用程序请求的大小添加8个字节
  • 调用系统内存分配例程(例如Windows中的HeapAlloc)
  • 在前8个字节中填写最初请求的大小
  • 将8添加到返回的指针,并将其返回给应用程序
delete运算符应执行相反的操作:

  • 从应用程序给定的指针中减去8个字节
  • 调用系统内存释放例程
如果这样做,请确保实现new和delete的所有风格(抛出和非抛出、new和new[]、delete和delete[]、…)

还要注意第三方库。他们有时在DLL的编译代码中调用new,但在头中调用delete。这意味着new和delete将使用不同的实现,您的应用程序将崩溃

编辑:

需要舍入到8字节的倍数并添加8字节,因为数据应存储在其大小的倍数的地址中:

  • 字符可以再存储
  • 短裤必须存放在均匀的地址上
  • long必须存储在4的倍数的地址上
  • double必须存储在8的倍数的地址上
因为double是我所知道的最大的本机数据类型,所以我们四舍五入到8字节的倍数,并添加8字节以确保满足这些要求。

  • 您可以重写
    new
    操作符来调用
    malloc()
    ,并将大小存储在全局
    std::map alloc
然后,这个
getmomeize()
函数的行为将与您想要的一样:

getSomeHow(void *p){
  return alloc[p]; 
}
  • 您还可以编写自己的malloc(),并将加载程序设置为使用您的malloc而不是标准的malloc。我这样做是为了追踪,效果很好
那太好了,但是为什么不分配一个稍大一点的块,在其开始处写入分配的大小,然后返回一个偏移指针呢?嗯,是的,实际上要好得多@Ben,你能给我一些提示如何写我自己的malloc吗?我很感兴趣。谢谢你advance@There我们无能为力:您正在运行哪个操作系统?您必须使用自己的malloc()realloc()和free()编写一个C文件(函数声明必须与stdlib.h中的函数声明相同)。然后将其编译为动态库(dll),并告诉系统加载malloc库。不幸的是,我不知道如何在Windows7中完成最后一件事。也许这里有人能帮上忙。为什么正好是8个字节,而“没有足够的字节来存储
大小\u t
变量”?因为本机数据类型需要存储在一个地址上,该地址是其大小的倍数。通常,最大的数据类型是double,即8字节。因此,我们需要向大小和指针添加8个字节,以使其保持8字节的倍数。(对我的帖子稍加修改,以确保我们保持8字节的倍数)。好的,我明白了。那么它不应该是
max(sizeof(double)、sizeof(void*)
或类似的东西,这样代码就可以移植到1024位(或其他)计算机上吗?你的意思是,以前分配给函数代码、线程控制流还是进程、堆上?