2011-09-24 102 views
0

我正在解决一个量子机器问题,它需要我通过操纵一些矩阵来找到一些特征值。这个问题的细节是不相关的,我只需要帮助C++的问题,我是这个语言的新手,几个小时后,我发现任何尝试自己解决这个问题都是徒劳的,所以我转向你寻求帮助。删除双指针(矩阵)

我有这个问题,其中glibc在我的程序结束时检测到错误,我无法正确释放,但在这里复制粘贴太大,所以我只会复制实际出现错误的部分。

void hamiltonian(int, double **&); 

int i,j; 

int main() 
{ 
int N = 1000; double **A; 

hamiltonian(N, A); 

//Physics here 
. 
. 
. 
. 
. 
//Delete 
for(i=0; i<N; i++){delete []A[i];} 
delete []A; 

return 0; 
} 

void hamiltonian(int N, double **&A) 
{ 
A = new double *[N]; 
for(i=0; i<N; i++) 
{ 
A[i] = new double[N]; 
for(j=0; j<N; j++) 
{ 
if(i==j)A[i][j] = 2; 
if(i==j+1 || i==j-1){A[i][j] = 1;} 
} 
} 
} 

根据我的教授我有同样的功能要解除我分配,但我压根没想到关于释放被几乎与我的项目完成后,所以我必须重新编写大量的代码,该问题是我不能在哈密尔顿函数内部释放A,因为我需要它在其他函数中(在物理内部)。

一定有办法解决这个问题吗?可能听起来有点无知,但这听起来像是一个效率较低的设计,如果我不得不按照我分配的相同函数进行释放。

+0

编辑添加删除[A]和A [1] =新的双[N]; – arynaq

+0

实现自己的矩阵功能对于学习C++可能行得通,但是如果你的主要目标是量子机器问题,找到一个能够在矩阵上操作并使用特征值的现有库不是更好吗? – maxim1000

+1

@ maxim1000是的,但它没有那么多的乐趣:p – arynaq

回答

2

根据我的教授我有同样的功能要解除我分配

这是纯粹的愚蠢。有时(几乎总是)您需要在函数外部使用分配的结构。对于对象来说肯定是错误的,因为构造函数和析构函数是不同的函数。

任何方式,你可以逃脱不使用类,如果你犯了一个矩阵struct和相关newMatrixdeleteMatrix功能:)

#include <cstddef> 
#include <iostream> 

using namespace std; 

struct Matrix 
{ 
    int n; 
    int m; 
    double** v; 
}; 

Matrix newMatrix (int n, int m) 
{ 
    Matrix A; 
    A.n = n; 
    A.m = m; 
    A.v = new double*[n]; 
    for(int i = 0; i < n; i++){ 
     A.v[i] = new double[m]; 
    } 
    return A; 
} 

Matrix newHamiltonianMatrix (int n, int m) 
{ 
    Matrix A = newMatrix(n, m); 
    for(int i = 0; i < A.n; i++){ 
     for(int j = 0; j < A.m; j++){ 
      A.v[i][j] = 0.0; 
      if(i == j){ 
       A.v[i][j] = 2.0; 
      } 
      if(i == j + 1 or i == j - 1){ 
       A.v[i][j] = 1.0; 
      } 
     } 
    } 
    return A; 
} 

void deleteMatrix (Matrix A) 
{ 
    for(int i = 0; i < A.n; i++){ 
     delete [] A.v[i]; 
    } 
    delete [] A.v; 
    A.v = NULL; 
} 

int main() 
{ 
    Matrix A = newHamiltonianMatrix(10, 20); 
    for(int i = 0; i < A.n; i++){ 
     for(int j = 0; j < A.m; j++){ 
      cout << A.v[i][j] << " "; 
     } 
     cout << endl; 
    } 
    deleteMatrix(A); 
} 
+0

将原始代码中的A = null设置为原始删除吗?会不会占用NxN双打成为0指针? – arynaq

+1

不,这并不会删除分配的double []和double [] []数组。 C++不使用垃圾回收(好吧,有第三方的GC库,但这是另一个话题) – Frigo

+0

谢谢,你的建议将为我省去重写我的整个代码的麻烦,我很乐意接受这个作为我的问题的答案,但希望有人会扩展为什么glibc不喜欢我删除我的矩阵。我认为我的教授意味着我必须用汉密尔顿语将它删除,因为glibc给了我一个错误,他的具体意思是这个,而不是一般的删除指针。我不明白删除逻辑在哈密尔顿函数之外不起作用。 – arynaq

2
delete A; 

需要是

delete[] A; 

如果你new[],您必须delete[]它。此外,请使用vector - 他们会自己照顾自己。

vector<vector<double>> matrix; 
+0

当然,我忘了[]中的[]上面的代码,它是在我的原始。我们不应该使用/构造类,这是计算物理学的一个类(主要是关于不同问题及其实现的算法,其中C++是由投票决定的)。 – arynaq

+0

@ user948652:如果你想编写C++,你必须使用类。这不是一个选项。谁决定不使用课程来教你分配是一个白痴,你应该开枪射击,然后再使用课堂。 – Puppy

+0

@DeadMG:除非我在标准中遗漏了一些不允许使用原始类型(基本类型数组)的规则,否则您的语句“*如果您想编写C++,您必须**使用类,它不是选项。*“是无稽之谈。 –

0

您的代码有几个问题。

(1)不分配存储器到的A指针成员。即A[i]未分配new[]。因此访问它们是未定义的行为

(2)如果分配给new[],您必须对指针做delete[]。在你的其他功能delete A;是错误的。使用delete[] A;

(3)使用new/new[]不是唯一的分配方式。事实上,你应该在没有选择的情况下使用这种动态分配。从你的代码看来,你是硬编码N=1000。所以最好使用2D数组。

const int N = 1000; // globally visible 
int main() 
{ 
    double A[N][N]; 
    ... 
} 
void hamiltonian (double (&A)[N][N]) 
{ 
    ... 
} 
+0

最后,“你必须在你分配的同一个函数中释放”这个想法完全是无稽之谈。 –

+0

回想起来,对整个600行进行复制可能更为明智,我犯了另一个错误(该文件在我的linux中,我在windows中)。我当然分配A [i] = new double [N];在循环内。至于第2点,如果你查看我对上一张海报的评论,也是另一个错误。 N也是一个输入变量,但为了简化我的问题,我只是将其设置为常量。 – arynaq

+0

-1为局部变量'double A [N] [N];'N = 1000?真的吗?结果是这个网站的名字。 –