指针数组与数组指针----从一维到二维

这是一个很容易混淆的概念

int *p1[5]int (*p2)[5]

第一个就是一个指针数组
[ ]的优先级比*高,所以p1会先于[ ]结合,成为数组,再和指针结合,成为数组指针,也就是数组中每一个元素都是一个指针

指针数组是数组,即-一个数组中,每个元素都是指针。

在这里插入图片描述

第二个就是一个数组指针
()的优先级比[ ]高,所以*p先构成一个指针,再和[ ]构成一个数组
所以p2是一个指针,指向的是包含5个int 数据的数组

数组指针是指针,即一个指向数组的指针

下面举一个例子

int arr[5]={12345};
int (*p1)[5] = &arr;
/*下面是错误的*/
int (*p2)[5] = arr;

我们都知道,数组名arr是数组首元素的地址,而&arr是整个数组的首地址
但是在c语言里面,上面的是正确的,下面的确是错误的

在 C 语言中,赋值符号“=”号两边的数据类型必须是相同的,如果不同,则需要显示或隐式类型转换。

在这里面,p1和p2都是数组指针,指向的是整个数组
而&arr是整个数组的首地址,也是指向的整个数组
但是,arr却是数组首元素的地址,指向的是单个元素,数据类型不一样,就会发生错误

下面我们来到二维数组
我们定义了一个二维数组

扫描二维码关注公众号,回复: 11279212 查看本文章
#include<iostream>
using namespace std;
int main()
{
	int a[2][3]={{1,2,3},{4,5,6}};
	cout<<"a的值是:"<<a<<endl;
	cout<<"*a的值是:"<<*a<<endl;
	cout<<"*a[0]的值是:" <<a[0]<<endl;
	cout<<"*a[0][0]的值是:" <<&a[0][0]<<endl;
	cout<<"a[0][0]的值是:" <<a[0][0]<<endl;
	return 0;
}

下面是他的运行结果
在这里插入图片描述
我们可以看到 a ,*a ,*a[0] ,*a[0][0],这四个值是一样的,那么是不是就代表他们四个也相同呢?
当然不,他们的类型不同
a 是整个数组的首地址,a[0] 是数组第一行的首地址,虽然值相同,但是含义不同,也就是类型不同
a 是相对于整个数组来说,a[0] 是相对于第一行来说
也就是,a是int *[3]类型

这里就需要再次说明一下为什么是int *[3]类型
p是一个指针变量,它指向包含3个int元素的一维数组,此时p的增量以它所指向的一维数组长度为单位;
(p+i)是一维数组a[i][0]的地址;
(p+2)+3表示a[2][3]地址(第一行为0行,第一列为0列),
(p+2)+3)表示a[2][3]的值。

a[0]是int *类型
如果将a[0] 改为&a[0] , 那么a和&a[0] 是相同的

在这里插入图片描述

下面我们再看一个例子,这道题的正确答案是c

A
定义了一个二维数组
看一下报错信息
在这里插入图片描述
提示类型转换错误
pa应该定义为 (*pa)[5] ,[ ]里面的数字应该是二维数组每一行元素的个数

B
定义了一个指针数组
后半句也是错误的
左边是一个数组,而右边只是一个元素的指针,类型不同

C
是正确的
定义了一个指针数组,c数组的每一个元素已经是指针了,再取数组名就又加了一个指针,左边也是指针的指针,类型相同

比如一维数组
int s[2]={1.2};
那么s就是1的指针
也就是说,只取数组名,就相当于加了一个指针,如果数组中的元素本来就是指针,那不就是指针的指针了么

D
右边是二级指针,左边只是一级指针,所以错误

就是说如果你将一个n级指针赋给指针变量,定义这个指针变量就得用n个*表示

猜你喜欢

转载自blog.csdn.net/qq_45721778/article/details/105650885