C++三维数组函数

例如,一个函数包含多维数组参数的函数可以定义为:

void procedure (int myarray[ ][3][4])

注意第一对括号[ ]中为空,而后面两对不为空。这是必须的,因为编译器必须能够在函数中确定每一个增加的维度的深度。
C++教程这里有点看不懂,为什么第一组要为空呢?

今天,一个学徒向我提出了问题,说是不管他怎么理解,对于多维数组和多维指针还是不太明白,嗯,耐心的讲解了一番……还好不负所望,他听懂了,不然的话,咱这块老脸可就丢大了:),整理了一下,把今天讲给他听的放到网上来,供遇到同样问题的朋友参考,有理解错误的地方,还请各位高手指点。首先C++为矩形数组,意味着 int[2][3] 等于 int[6],int[2][3][4] 等于 int[24] 那为什么还需要多维数组?一维数组完全能完成多维数组的功能啊。原因是,这是为了方便算法的科学计数吧。就像一千万可以表示为:1000000 也可以表示为 0.1X10的8次方。int a[2] 这是一个一维数组,int *p=a,p是指向这个数组的指针。a存储的是这个数组内存的首地址,也就是说 a 等于 p 等于 数组内存首地址,所以,a[0] 的值等于 *p 等于 首个元素的值。思考,如果现在需要扩充这个数组怎么办呢?我们知道,一维数组a存储的是数组内存的首地址(a[0],a[1] 才是数组元素的值),那如果把 a[0] 的值换成另一个数组的内存首址,那不是就可以扩充这个数组了吗(前面说过C/C++用的是矩形数组,意味着,如果数组a里的任何元素存储了另一个数组的首地址,那么其它元素的存储值也必需是内存首地址)?假设,又定义了两个数组 : int aa[3],ab[3] 把 aa 首地址给a[0] ,把 ab 首地址给 a[1] ,这就形成了“数组的数组” ,即:一个数组内的元素值是了另一个数组的内存首地址,定义方法:int a[2][3],表示:我定义了一个数组,有两个元素,而每个元素的值,存储的是另一个 包含三个元素的 数组内存首地址。要怎么使用?首先,如果要访问上面假设的aa[0] 那么使用 a[0][0] ,要访问 ab[0] 使用 a[1][0] ,好了,下标访问解决了,那这就行了吗?不行,还有指针啊,一维数指可以用指针来操作,那二维数组呢?当然也可以……int a[2] ,是一个一维数组,它存储了两个 int 型。每个 int 型 使用 sizeof(int) 得出,占用四个字节。那么 sizeof(a[0]) 等于4 ,sizeof(a)等于 sizeof(a[0]) 乘以 2 等于 8。也就是说,使用 int 指针,偏移两次(每次4字节),就可以操作这个数组的值。而在 int a[2][3] 里,a[0] 还是占用4字节吗?当然不是,前面说过,它的每个元素包含了另外一个数组,这时候的 a[0] 占用了 sizeof (a[0]) 等于 int (4字节) 乘以 3 等于 12字节……使用 int 型指针 每次++只能偏移 4 个字节,而我们现在需要的是 从 a[0] 偏移到 a[1] --12个字节,那怎么办? int(4字节) 乘以 3,所以定义 int (*p)[3],注意这里,不是使用 int *p[3],而是使用int (*p)[3],为什么要个括号?因为,int *p[3],定义的是一个指针数组,它可以这么用:int a,b,c,*p[3]; p[0]=&a;p[1]=&b;p[2]=&c,那么我们p[n]实施++操作的时候,它一样的只是偏移4个字节。而 int (*p)[3],就不同了,它是一个数组指针,每次对它进行++操作时,它正确的偏移了12个字节。好了,现在可以这么使用指针了,int a[2][3],(*p)[3];p=a;p++; 可以从a[0]偏移到a[1]了,但是,要取得a[0][0]的值怎么办呢?前面说过,这个a是数组的数组,意味着a[0] 值是另一个数组的首地址,所以我们可以使用 int 型指针,来把 a[0] 当做一个一维数组来操作了。int *pp;pp=*p(注意,是pp=*p,而不是pp=p ,p的值是这个二维数组a的首地址,*p的值就是a[0]的值,存储的是 包含三个元素的 数组首地址。)那么,pp++,int 型 偏移 4 字节 ,能正常读取了,顺理成章~~~:)那如果int [2][3][4]呢?不说啦,思路延伸一下就行了。追问

好一个复制粘贴

温馨提示:答案为网友推荐,仅供参考
第1个回答  推荐于2016-10-04
因为数组名的本质是数组的首地址,你传入的只是一个指针变量,C++编译器不会帮你检查长度也不允许你把长度传入。
编译器计算数组偏移量的过程是这样的
你定义 int a[5][3];
那么a[i][j] 就等价于 a[i*3+j],你不给出后面维度的长度就编译器就无法计算。
理解C数组的本质这个问题就会容易解答。本回答被提问者采纳
第2个回答  2014-08-20
这个传入的是数组的 第一个数据的 地址, 并不是数据值。
一维时 int myarray[](第一个地址用myarray[]表示)
二维时 int myarray[][3](第一个地址用myarray[][3]表示)
三维时 int myarray[][3][4](第一个地址用myarray[][3][4]表示)
以此类推。
第3个回答  推荐于2018-04-13
常量和变量可以用作函数实参,同样数组元素也可以作函数实参,其用法与变量相同。数组名也可以作实参和形参,传递的是数组的起始地址。
用数组元素作函数实参
由于实参可以是表达式,而数组元素可以是表达式的组成部分,因此数组元素当然可以作为函数的实参,与用变量作实参一样,将数组元素的值传送给形参变量。
【例5.6】用函数处理例5.5。
算法和例5.5是一样的,今设一函数max_value,用来进行比较并返回结果。可编写程序如下:
#include <iostream>
using namespace std;
int main( )
{
int max_value(int x,int max); //函数声明
int i,j,row=0,colum=0,max
int a[3][4]={{5,12,23,56},{19,28,37,46},{-12,-34,6,8}}; //数组初始化
max=a[0][0];
for (i=0;i<=2;i++)
for (j=0;j<=3;j++)
{
max=max_value(a[i][j],max); //调用max_value函数
if(max==a[i][j])//如果函数返回的是a[i][j]的值
{
row=i; //记下该元素行号i
colum=j; //记下该元素列号j
}
}
cout<<"max="<<max<<",row="<<row<<",colum="<<colum<<endl;
}
int max_value(int x,int max)//定义max_value函数
{
if(x>max) return x;//如果x>max,函数返回值为x
else return max;//如果x≤max,函数返回值为max
}
#include <iostream>
using namespace std;
int main( )
{

int max_value(int x,int max); //函数声明

int i,j,row=0,colum=0,max

int a[3][4]={{5,12,23,56},{19,28,37,46},{-12,-34,6,8}}; //数组初始化

max=a[0][0];

for (i=0;i<=2;i++)

for (j=0;j<=3;j++)

{

max=max_value(a[i][j],max); //调用max_value函数

if(max==a[i][j])//如果函数返回的是a[i][j]的值

{

row=i; //记下该元素行号i

colum=j; //记下该元素列号j

}

}
cout<<"max="<<max<<",row="<<row<<",colum="<<colum<<endl;
}
int max_value(int x,int max)//定义
max_value函数
{

if(x>max)
return x;//如果x>max,函数返回值为x

else return max;//如果x≤max,函数返回值为max
}
用数组名作函数参数
可以用数组名作函数参数,此时实参与形参都用数组名(也可以用指针变量,见第6章)。

【例5.7】用选择法对数组中10个整数按由小到大排序。

所谓选择法就是先将10个数中最小的数与a[0]对换,再将a[1]到a[9]中最小的数与a[1]对换……每比较一轮,找出一个未经排序的数中最小的一个。共比较9轮。根据此思路编写程序如下: 复制纯文本新窗口
#include <iostream>
using namespace std;
int main( )
{
void select_sort(int array[],int n); //函数声明
int a[10],i;
cout<<"enter the originl array:"<<endl;
for(i=0;i<10;i++) //输入10个数
cin>>a[i];
cout<<endl;
select_sort(a,10);//函数调用,数组名作实参
cout<<"the sorted array:"<<endl;
for(i=0;i<10;i++) //输出10个已排好序的数
cout<<a[i]<<" ";
cout<<endl;
return 0;
}
void select_sort(int array[],int n) //形参array是数组名
{
int i,j,k,t;
for(i=0;i<n-1;i++)
{
k=i;
for(j=i+1;j<n;j++)
if(array[j]<array[k]) k=j;
t=array[k];array[k]=array[i];array[i]=t;
}
}
#include <iostream>
using namespace std;
int main( )
{
void select_sort(int array[],int n); //函数声明

int a[10],i;

cout<<"enter the originl array:"<<endl;

for(i=0;i<10;i++) //输入10个数

cin>>a[i];
cout<<endl;
select_sort(a,10);//函数调用,数组名作实参
cout<<"the sorted array:"<<endl;
for(i=0;i<10;i++) //输出10个已排好序的数

cout<<a[i]<<" ";

cout<<endl;

return 0;
}
void select_sort(int array[],int n) //形参array是数组名
{

int i,j,k,t;

for(i=0;i<n-1;i++)

{

k=i;

for(j=i+1;j<n;j++)

if(array[j]<array[k]) k=j;

t=array[k];array[k]=array[i];array[i]=t;
}
}
运行情况如下:
enter the originl array:
6 9 -2 56 87 11 -54 3 0 77↙ //输入10个数
the sorted array:
-54 -2 0 3 6 9 11 56 77 87

关于用数组名作函数参数有两点要说明:
1) 如果函数实参是数组名,形参也应为数组名(或指针变量),形参不能声明为普通变量(如int array;)。实参数组与形参数组类型应一致(现都为int型),如不一致,结果将出错。

2) 需要特别说明的是: 数组名代表数组首元素的地址,并不代表数组中的全部元素。因此用数组名作函数实参时,不是把实参数组的值传递给形参,而只是将实参数组首元素的地址传递给形参。

形参可以是数组名,也可以是指针变量,它们用来接收实参传来的地址。如果形参是数组名,它代表的是形参数组首元素的地址。在调用函数时,将实参数组首元素的地址传递给形参数组名。这样,实参数组和形参数组就共占同一段内存单元。见图5.6。
图5.6
在用变量作函数参数时,只能将实参变量的值传给形参变量,在调用函数过程中如果改变了形参的值,对实参没有影响,即实参的值不因形参的值改变而改变。而用数组名作函数实参时,改变形参数组元素的值将同时改变实参数组元素的值。在程序设计中往往有意识地利用这一特点改变实参数组元素的值。

实际上,声明形参数组并不意味着真正建立一个包含若干元素的数组,在调用函数时也不对它分配存储单元,只是用array[]这样的形式表示array是一维数组名,以接收实参传来的地址。因此array[]中方括号内的数值并无实际作用,编译系统对一维数组方括号内的内容不予处理。形参一维数组的声明中可以写元素个数,也可以不写。

函数首部的下面几种写法都合法,作用相同:
void select_sort(int array[10],int n) //指定元素个数与实参数组相同
void select_sort(int array[],int n) //不指定元素个数
void select_sort(int array[5],int n) //指定元素个数与实参数组不同

在学习第6章时可以进一步知道,C++实际上只把形参数组名作为一个指针变量来处理,用来接收从实参传过来的地址。前面提到的一些现象都是由此而产生的。

用多维数组名作函数参数
如果用二维数组名作为实参和形参,在对形参数组声明时,必须指定第二维(即列)的大小,且应与实参的第二维的大小相同。第一维的大小可以指定,也可以不指定。如:
int array[3][10]; //形参数组的两个维都指定

int array[][10]; //第一维大小省略
二者都合法而且等价。但是不能把第二维的大小省略。下面的形参数组写法不合法:
int array[][]; //不能确定数组的每一行有多少列元素
int array[3][]; //不指定列数就无法确定数组的结构
在第二维大小相同的前提下,形参数组的第一维可以与实参数组不同。例如,实参数组定义为:
int score[5][10];
而形参数组可以声明为:
int array[3][10]; //列数与实参数组相同,行数不同
int array[8][10];
这时形参二维数组与实参二维数组都是由相同类型和大小的一维数组组成的,实参数组名score代表其首元素(即第一行)的起始地址,系统不检查第一维的大小。

如果是三维或更多维的数组,处理方法是类似的。

【例5.8】有一个3×4的矩阵,求矩阵中所有元素中的最大值。要求用函数处理。

解此题的算法已在例5.5中介绍。程序如下: 复制纯文本新窗口
#include <iostream>
using namespace std;
int main( )
{
int max_value(int array[][4]);
int a[3][4]={{11,32,45,67},{22,44,66,88},{15,72,43,37}};
cout<<"max value is "<<max_value(a)<<endl;
return 0;
}
int max_value(int array[][4])
{
int i,j,max;
max=array[0][0];
for( i=0;i<3;i++)
for(j=0;j<4;j++)
if(array[i][j]>max) max=array[i][j];
return max;
}
#include <iostream>
using namespace std;
int main( )
{
int max_value(int array[][4]);
int a[3][4]={{11,32,45,67},{22,44,66,88},{15,72,43,37}};

cout<<"max value is "<<max_value(a)<<endl;
return 0;
}
int max_value(int array[][4])
{

int i,j,max;
max=array[0][0];

for( i=0;i<3;i++)

for(j=0;j<4;j++)

if(array[i][j]>max) max=array[i][j];

return max;
}运行结果如下:
max value is 88本回答被网友采纳
第4个回答  2014-08-20
可能是传入的数组的第一维大小不一定吧

相关了解……

你可能感兴趣的内容

本站内容来自于网友发表,不代表本站立场,仅表示其个人看法,不对其真实性、正确性、有效性作任何的担保
相关事宜请发邮件给我们
© 非常风气网