在函数中使用二维数组

Using a 2-d Array in a function

本文关键字:二维数组 函数      更新时间:2023-10-16

我正在尝试解决一个动态编程问题,我需要以二维数组的形式获取用户输入,并在函数中使用二维数组中的值。在函数中使用 2-D 数组的值时不会更改。

在函数 int dp 中,我得到了 错误:

将"a"声明为多维数组必须具有除第一个维度之外的所有维度的边界

int max(int a,int b,int c)
{
if(a>=b && a>=c)return a;
if(b>=c && b>=a)return b;
else return c;
}
int max2(int a,int b)
{
if(a>b)return a;
else return b;
}

int dp(int i,int j,int a[][],int p,int q)
{
if((i-1)>=0 && (j-1)>=0 &&(i+1)<p &&(j+1)<q )
return  max(a[i][j]+dp(i-1,j+1,a,p,q),a[i][j]+dp(i+1,j+1,p,q),    
    a[i][j]+dp(i,j+1,p,q));
if(i==0 && j!=0 && (j+1)<q)
return max2(a[i][j]+dp(i+1,j+1,p,q),a[i][j]+dp(i,j+1,p,q));
}
int main()
{
int p,q,r,s,T,a,b,i,j,k;
scanf("%d",&T);
for(a=0;a<T;a++)
{
    scanf("%d %d",p,q);
    int z[p][q];
    int max=0;
    for(i=0;i<q;i++)
    {
        for(j=0;j<p-1;j++)
        scanf("%d ",&z[j][i]);
        scanf("%d",&z[j+1][i]);
    }
    for(i=0;i<p;i++)
   {
    if(dp(i,0,z,p,q)>max)
    max=dp(i,0,z,p,q);
   }
  }
   }

这一切都在错误消息中:

将"a"声明为多维数组必须具有除第一个维度之外的所有维度的边界

您的函数签名没有a的第二维边界:

int dp(int i,int j,int a[][],int p,int q)
//                     ^^^^^

您需要用a[][N]填写它,N是正确的界限。问题是您在此处使用 VLA:

scanf("%d %d",p,q);
int z[p][q];

这是非标准的C++,基本上意味着你不能写dp的签名,因为第二个边界必须被称为编译时常量。你可以把它变成一个一维数组:

int* z = new int[p*q];
int dp(int i, int j, int* a, int p, int q)
//                   ^^^^^^

或者在 2 个维度中动态分配它,然后以这种方式传递它:

int** z = new int*[p];
for (int i = 0; i < p; ++i) {
    z[i] = new int[q];
}
int dp(int i, int j, int** a, int p, int q)
//                   ^^^^^^^
函数

dp需要一些信息来执行有意义的索引计算,无论是由编译器完成还是在实际安装中完成。必须在类型中指定维度,或者参数a可以是类型 int**,而其维度作为单独的参数提供给dp 。由于这是C++,因此一种std::vector< std::vector< int > >可能更适合该任务。

您会收到该错误,因为您不能在函数声明中将索引(行,列)都留空int a[][]。必须同时指定或至少具有列索引的值。

使用动态声明

int **z = new int*[p];
for (int i = 0; i < p; i++) 
    z[i] = new int[q];

将参数int a[][]更改为int **a

您不能在堆栈上动态声明数组,因为必须在编译时知道大小。执行此操作的唯一方法是使用 new 关键字为堆上的数组分配内存,然后可以在运行时声明大小。

然而,更容易的是使用容器类,或者在你的情况下,使用容器的容器,如整数向量;

#include <vector>
vector< vector<int> > arrArray(rows, vector<int>(columns)); 

语法可能看起来有点奇怪,但分解一下;

vector<int> - int 型向量

vector< vector<int> > - int 型向量的向量

arrArray(rows, vector<int>(columns)); - 在第一个参数中,我们说;在我们的数组中创建rows数量的vector<int>,第二个参数将数组启动到某个值。如果它只是一个 2D int数组,我们可能会将其启动到 0 中,或者省略第二个参数并依赖默认值 int。但是,因为我们的多维向量也包含向量,所以我们设置主向量的每一行来存储一个int向量,该向量容纳columns数量的整数。

现在,您可以像访问任何其他阵列一样访问该阵列;

arrArray[2][0] = 5;

您还可以获得容器类包含的所有附加优势,包括迭代器和许多用于操作和检查数组的有用类方法。了解创建容器类的语法后,您会发现它们比数组更容易使用。您也不必担心必须管理自己的内存,并且能够在访问矢量元素之前进行边界检查。