delete(非数组形式)是否知道new或new[]分配的内存总量
Does delete (non array form) know the total amount of memory allocated by either new or new[]
这个问题是在调用析构函数后是否删除[]一次性释放内存?但作为一个单独的问题离开了。
似乎(如果错误,请纠正我(delete
和delete[]
之间的唯一区别是delete[]
将获取数组大小信息并调用所有数组的析构函数,而delete
将析构函数中唯一的第一个。特别地,delete
还可以访问关于new[]
分配了多少总内存的信息。
如果不关心破坏动态分配的数组元素,而只关心由new
或new[]
分配的内存被释放,那么delete
似乎能够做同样的工作。
This How do delete[]";知道";操作数数组的大小?这个问题的公认答案有一条来自@AnT的评论,我引用
还要注意,数组元素计数器仅用于具有非平凡析构函数的类型。对于具有琐碎析构函数的类型,计数器不是由new[]存储的,当然也不是由delete[]检索的
这条注释表明,通常delete
表达式知道分配的整个内存量,因此知道最终在一次释放多少内存,即使内存包含一个元素数组。所以如果有人写
auto pi = new int[10];
...
delete pi;
尽管标准认为这是UB,但在大多数实现中,这不应该泄露内存(尽管它不是可移植的(,对吧?
在C++标准下,在分配了new[]
的东西上调用delete
只是未定义的行为,在分配有new
的东西上呼叫delete[]
也是如此。
在实践中,new[]
将通过类似malloc
的东西来分配内存,new
也是如此。delete
将销毁指向的对象,然后将内存发送到类似free
的对象。delete[]
将销毁数组中的所有对象,然后将内存发送给类似free
的对象。new[]
可以分配一些额外的存储器以传递给delete[]
,从而给delete[]
要销毁或不销毁的元素的数量。
如果使用实际的malloc
/free
,那么一些实现将允许使用指向malloc块中任何位置的指针。其他人不会。需要将与从malloc
获得的值完全相同的值传递给free
才能定义该值。这里有一个问题,如果new[]
为数组大小/元素步长留出了一些额外的空间,并将其固定在块之前,则delete
将向第一个元素传递指针,然后delete
将向free
传递与从malloc
获得的new[]
不同的指针。(我认为有一种架构会发生这样的事情。(
与大多数未定义的行为一样,您不能再依赖于审核您编写的代码,而是现在致力于审核生成的程序集和与您交互的C/C++标准库,然后才能确定要执行的行为是否正确。在实践中,这是一个无法实现的负担,因此您的代码最终会具有负值,即使您在实际检查时检查了事情的工作方式。如何确保每次更改编译器版本、标准库版本、操作系统版本、系统库或编译器时都会进行相同的检查(对生成的二进制文件及其行为(?
这是正确的。delete和delete[]的区别在于,后者知道数组中分配的项数,并对其上的每个对象调用析构函数。为了100%正确,两者实际上都"知道"它——为数组分配的项数等于分配的内存大小(两者都知道(除以对象的大小。
有人可能会问,为什么我们需要delete[]和delete than——为什么delete不能执行相同的计算?答案是多态性。当通过指向基类的指针进行删除时,分配的内存大小将不等于静态对象的大小。
另一方面,delete[]没有考虑对象被多态化的可能性,这就是为什么动态数组永远不应该被视为多态对象(即分配和存储为基类的指针(。
对于泄漏内存,在阵列上使用POD类型的情况下,delete不会泄漏内存。
避免所有构造引发未定义行为的一个具体原因是,编译器有权假设从未发生过未定义行为,即使您看不出它们可能会出错。例如,给定这个程序。。。
#include <iostream>
#include <cstring>
int main(int argc, char **argv)
{
if (argc > 0) {
size_t *x = new size_t[argc];
for (int i = 0; i < argc; i++)
x[i] = std::strlen(argv[i]);
std::cout << x[0] << 'n';
delete x;
}
return 0;
}
编译器可能会发出与…相同的机器代码。。。
int main(void) { return 0; }
因为CCD_ 35控制路径上的未定义行为意味着编译器可能认为该路径从未被占用。
- 哪些资源是由智能指针管理的,而它们的内存不是由new分配的
- C++ 使用 'new' 分配顺从内存分配
- 使用运营商New分配的数据结构是否有任何副作用
- 未'new'分配给指针而创建的对象的生存期
- 用new分配4k int后的内存覆盖
- 使用free()释放new分配的内存空间
- 如果通过委托给“malloc”的重载“new[]”分配,“释放”内存是否安全
- 使用 init 方法来避免使用 new 分配对象是这种糟糕的设计
- delete命令会清除用new分配的内存吗
- new分配了多少字节
- C++本地对象超出范围,返回指针(使用new分配的内存).因此内存泄漏
- 检索在函数内部使用运算符new分配的类指针对象成员的值时出现的问题
- 递归删除链表,使用 new 分配内存
- 从函数返回指向对象的指针,而不使用 new 分配指针
- 删除使用placement new分配的动态多态对象
- C++new分配的空间比预期的要多
- 如何在char*func()中正确删除用new[]分配的char数组
- new[]分配的内存大小
- 是未使用在堆栈或堆上分配"new"分配的对象
- delete(非数组形式)是否知道new或new[]分配的内存总量