嗨,我对C ++很陌生,我需要动态分配二维数组。没有错误,但在运行时,当我设置订单和第一行时,我得到一个运行时错误:“Segmentation Fault”...这里是代码:
#include <iostream>
using namespace std;
double ** allocateDynamicArray(int &order){
double ** arr = new double *[order];
for(int i = 0;i < order; i++){
*arr = new double[order+1];
}
return arr;
}
void deallocateDynamicArray(double **arr, int order){
for(int i=0; i<order; i++){
delete [] arr[i];
}
delete [] arr;
}
void addAndPrintArray(double **arr, int order){
cout << "Zadejte prvky pole radu " << order << endl;
for(int i=0; i< order; i++){
for(int j=0; j< order+1; j++){
cout << "Pole[" << i << "][" << j << "]: ";
cin >> arr[i][j];
}
}
for(int i=0; i< order; i++){
for(int j=0; j< order+1; j++){
cout << arr[i][j] << " ";
if(arr[i][j] < 10 && arr[i][j] > -10){
cout << " ";
}
cout << endl;
}
}
}
int main()
{
int order;
cin >> order;
double **dynArray = allocateDynamicArray(order);
addAndPrintArray(dynArray, order);
deallocateDynamicArray(dynArray, order);
return 0;
}
答案 0 :(得分:3)
您忘记在初始化循环中增加arr
:
for(int i = 0;i < order; i++){
*arr = new double[order+1];
请改为:
for(int i = 0;i < order; i++){
arr[i] = new double[order+1];
此外,除非您要更改其中一行的尺寸,否则与分配二维数组的方式相比,上述方法效率低:
double ** allocateDynamicArray(int &order){
double ** arr = new double *[order];
int cols = order+1;
double *pool = new double [order * cols];
for(int i = 0;i < order; i++, pool += cols){
arr[i] = pool;
}
return arr;
}
void deallocateDynamicArray(double **arr){
delete [] arr[0];
delete [] arr;
}
只需两次调用new[]
,只需要调用delete[]
两次,无论行数和列数如何。
上述第二种形式优于第一种形式的另一个原因是new[]
可能会引发异常。
使用第一个表单,如果该循环中的某个位置new[]
抛出异常,则必须跟踪所有先前成功的分配,并通过发出delete[]
个调用来“回滚” 。不太好。
使用第二种形式,如果第一次调用new[]
失败,则没有任何损害,因为异常将在没有泄漏的情况下抛出(因为没有成功分配内存)。如果对new[]
的第二次调用失败,您需要做的就是提供(在catch
块内)删除对new[]
的第一次调用。
double ** allocateDynamicArray(int &order) {
double ** arr = new double *[order];
int cols = order+1;
try {
double *pool = new double [order * cols];
}
catch (std::bad_alloc& e)
{
delete [] arr; // delete previous allocation
return NULL; // or rethrow the exception here
}
for(int i = 0;i < order; i++, pool += cols)
arr[i] = pool;
return arr;
}
请注意,std::vector
可以帮助您完成所有这些工作。但是,如果由于某种原因你不能使用向量,并且二维数组在其整个生命周期中将保持相同的大小,请使用第二种形式。
此外,第二种方法减少了堆的内存碎片。而不是对分配器的rows
调用,只对分配器进行一次调用以分配数据。如果rows
为1,000或10,000,则您立即看到最好拨打new[]
两次电话,而不是拨打new[]
的10,000次电话。
答案 1 :(得分:1)
替换
double ** arr = new double *[order];
for(int i = 0;i < order; i++){
*arr = new double[order+1];
与
double ** arr = new double *[order];
for(int i = 0;i < order; i++){
arr[i] = new double[order+1];
在您目前的代码中,您只初始化第一个数组元素。