问题:变量 n 的值是多少,以下代码会导致内存泄漏?
这就是代码:
int* Bar(int n)
{
if (n == 1)
throw "exception";
return new int[n];
}
void Foo(int n)
{
int *a = Bar(n);
if (n <= 2)
return;
delete[] a;
}
从5.3.4 / 7
当表达式的值在 direct-new-declarator是零, 调用分配函数 分配一个没有元素的数组。
从3.7.3.1/2
取消引用指针的效果 作为零大小的请求返回 未定义。
另外
即使空间的大小 要求[由新]为零, 请求可能会失败。
这意味着你可以做到,但你可以 不合法(以明确的方式 跨所有平台)取消引用 你得到的记忆 - 你只能 传递给数组删除 - 和你 应该删除它。
这是一个有趣的脚注(即 不是标准的规范部分, 但包含在说明性的puprposes) 附在句子上 3.7.3.1/2
[32。目的是让操作员 new()可通过调用实现 malloc()或calloc(),所以规则是 基本相同。 C ++不同 来自C要求零请求 返回一个非空指针。]
int * a = Bar(1)和Bar(1)抛出异常。它是变量a的构造函数中的异常吗?它会导致内存泄漏吗?
答案 0 :(得分:7)
如果a == 0或a == 2,可能会导致它们。
如果a == 1抛出异常并且没有分配内存。如果a> 2内存分配和释放。
如果必须分配== 0内存,因为不允许new返回空指针。您必须使用delete []释放已分配的内存。
如果分配了== 2内存并且函数返回。这是一个明显的泄漏。
答案 1 :(得分:2)
If n < 0 you'll more likely get exception std::bad_alloc (because of n will be converted to size_t which is unsigned) - no memory leak. If n == 1 you'll get exception (invoked by `throw "exception"`) - no memory leak. If n == 0 || n == 2 you'll never call delete - memory leak. If n > 2 you'll call delete - no memory leak.
答案 2 :(得分:0)
不,如果我正确理解你的问题,bar函数将抛出异常并且Foo函数实际上从未捕获它,这意味着它也将传递出该函数。但不,它不应该导致内存泄漏,因为你在分配之前抛出。
答案 3 :(得分:0)
您的评估大多是正确的 - n = 2会导致内存泄漏,n = 0理论上会导致内存泄漏 - n = 1会抛出异常(因此永远不会执行新的int),因此没有内存泄漏。
n的任何值&gt; 2不会导致内存泄漏。
现在如果n&lt; 0 - 你有未定义的行为 - 你可能会得到一个内存泄漏(这是一个负的int可以转换为一个大的正无符号值 - 可能会发生坏事)
答案 4 :(得分:0)
由于没有捕获异常的捕获器,它将继续进行并返回。 但由于我们声明为整数指针,如果将'n'发送为零,将创建一个默认指针。您也可以检查指针的大小。但它不会导致任何内存泄漏。后面的原因是,当你执行返回时,因为它是一个单个整数指针并且是一个局部变量,所以默认情况下释放占用的内存。 因此,在您提到的情况下,将不会发生内存泄漏。
答案 5 :(得分:0)
是的,0
和2
会导致内存泄漏。
这也是管理动态内存的非常糟糕的做法。 在C ++上,创建一个管理内存的类是很自然/更好的方法(例如,在构造函数中它分配一些内存,在析构函数中它会释放它)。这将更加无泄漏和更安全