如果二维数组大小要在运行的时候才能确定,只能开在堆区,在C++里面在堆区分配内存用的是运算符new,它返回它操作数类型的指针。但是它不能直 接开两个维数都不确定的二维数组,下面介绍几种开二维数组的方法。另外在用完了数组后,一定要记得清理内存,在C++里用运算符delete,对于清理数 组用delete[] ,如果忘了写最后几行代码,就是C++里最常见的内存泄露问题。
1.
A (*ga)[n] = new A[m][n];
...
delete []ga;
缺点:n必须是已知
优点:调用直观,连续储存,程序简洁(经过测试,析构函数能正确调用)
本人测试结果:在vc6.0下测试报错
2. A** ga = new A*[m];
for(int i = 0; i < m; i++)
ga[i] = new A[n];
...
for(int i = 0; i < m; i++)
delete []ga[i];
delete []ga;
缺点:非连续储存,程序烦琐,ga为A**类型
优点:调用直观,n可以不是已知
本人测试结果:在vc6.0下测试运行ok
3. A* ga = new A[m*n];
...
delete []ga;
缺点:调用不够直观
优点:连续储存,n可以不是已知
本人意见:此方法比较保险,用一维数组来表示二维数组,但是需要进行一维下标到二维下标的映射。
下面的方法主要运用了vector模板相关知识:
4. vector<vector<A> > ga;
ga.resize(m); //这三行可用可不用
for(int i = 1; i < n; i++) //
ga[i].resize(n); //
...
缺点:非连续储存,调试不够方便,编译速度下降,程序膨胀(实际速度差别不大)
优点:调用直观,自动析构与释放内存,可以调用stl相关函数,动态增长
5. vector<A> ga;
ga.resize(m*n);
方法3,4的结合
附:
2的改进版(Penrose提供,在此感谢)
A** ga = new A*[m];
ga[0] = new A[m*n];
for(int i = 1; i < m; i++)
ga[i] = ga[i-1]+n;
...
delete [] ga[0];
delete [] ga;
缺点:程序烦琐,ga为A**类型
优点:连续储存,调用直观,n可以不是已知
下面是一些错误和没成功的版本
1. A* ga = new A[m][n];
必然错误,前后的类型就不一致。
2. vector<A[n]> ga;
ga.resize(m);
gcc 3.2下编译失败,不知道其它编译器效果如何
也不知道标准是否允许
函数参数也可以是二维及及更高维数组。但必须指定除最高维以后的各维大小。这一点和初始化时,可以省略不写最高维大小的规则一致:
//定义一个使用二维数组作为参数
void Func(int arr[][5]) //第二维的大小可以不指定
{
...
}
//定义一个使用三维数组作为参数
void Func(int arr[][2][5]) //第三维的大小可以不指定
{
...
}