C++ 将向量转换为数组。如何释放内存?

C++ 将向量转换为数组。如何释放内存?,c++,arrays,pointers,vector,C++,Arrays,Pointers,Vector,我正在将一个双精度向量转换为一个双精度数组,如图所示: 不同之处在于,我希望将指针a作为函数参数返回: void getArray(double* a) { std::vector<double> v; a = &v[0]; } void getArray(双*a) { std::向量v; a=&v[0]; } 所以我的问题是,a的内存何时被释放?或者我必须自己调用delete[]a,这似乎很奇怪,因为我没有用new分配内存。我已经阅读了对上述答案的评论,

我正在将一个双精度向量转换为一个双精度数组,如图所示:

不同之处在于,我希望将指针a作为函数参数返回:

void getArray(double* a)
{
    std::vector<double> v;
    a = &v[0];
}
void getArray(双*a)
{
std::向量v;
a=&v[0];
}

所以我的问题是,
a
的内存何时被释放?或者我必须自己调用
delete[]a
,这似乎很奇怪,因为我没有用
new
分配内存。我已经阅读了对上述答案的评论,但我仍然不清楚。

当向量
v
被破坏时,
a
指向的内存将被释放。在本例中,这是函数的末尾,请不要执行以下操作:

void getArray(double* a)
{
    std::vector<double> v;
    a = &v[0];
} // The vector is destroyed here, and the memory
  // is deallocated.

此实现将调用未定义的行为,因为
v
是本地的:

void getArray(double* a)
{
    std::vector<double> v;
    a = &v[0]; // would be a UB for returning the pointer to internals of a local variable.
}
调用方应按如下方式使用它:

vector<double> data;
data.push_back(...);
... // populate the vector
double *tmp = getArray(data);
... // Use the array
delete[] tmp; // Avoid memory leaks
矢量数据;
数据。推回(…);
... // 填充向量
double*tmp=getArray(数据);
... // 使用数组
删除[]tmp;//避免内存泄漏
a的内存何时释放

a
指针本身是一个局部变量,因此它在其作用域的末尾被释放

a
指向向量
v
分配的内存。指向的内存在
v
的析构函数中解除分配(如果向向量添加对象或从向量中删除对象,也可以解除分配内存)。因为
v
是一个局部变量,它在作用域的末尾被销毁

或者我必须自己调用delete[]a

不,因为内存属于vector对象,但也因为

这似乎很奇怪,因为我没有分配新的内存

没错。您没有调用
new[]
,因此您没有调用
delete[]



请注意,
v[0]
具有未定义的行为,因为向量是空的。

a
将指向垃圾,一旦
v
超出范围,就没有什么可删除的。
a
的内存将在函数返回后立即释放,因为
a
是一个指向向量元素的指针,并且“v”是函数的本地值。另外,在UB旁边,从c++11开始,不那么粗俗的版本是
v.data()
而不是
&v[0]
,请参见“我正在将一个双精度向量转换为一个双精度数组”-为什么?无论如何,忘了
getArray
函数,只要在你的程序中使用向量,并在向量不能使用的地方使用
v.data()
(例如C接口),确保所使用的数据在向量的时间线内,这在你的例子中不是Andrew的回答中已经提到的情况。我不认为有ub,因为正如你所说,对a的任何修改都是函数的局部修改。@tobi在访问未使用大小构造的向量的
v[0]
时存在UB。@Andrew啊,是的,我认为他指的是取消对无效指针的引用(实际上“…因为
v
是局部的”是误导)考虑以注释的形式添加方法文档。嗯,当返回原始指针时,这是一个很好的实践。@Basilevs取决于OP试图做什么。你想什么时候销毁内存?谁应该管理这个?@basilev内存管理的一个好方法是将向量作为一个向量,让它管理内存,而不是自己手动管理它。这真的取决于最终目标。不应该做的事情的示例用法可能表明这是正确的事情。现代C++程序员应该尽量避免原始指针。
double *getArray(const vector<double>& v) {
    double *res = new double[v.size()];
    std::copy(v.begin(), v.end(), res);
    return res;
}
vector<double> data;
data.push_back(...);
... // populate the vector
double *tmp = getArray(data);
... // Use the array
delete[] tmp; // Avoid memory leaks