就按照你举的例子来说:
a[2][3]={0,1,2,3,4,5}
这时形成一个二维数组,元素是:
a[0][0]=0,物理地址&a[0][0]
a[0][1]=1,地址&a[0][0]+1
a[0][2]=2,地址&a[0][0]+2
a[1][0]=3,地址&a[0][0]+3
a[1][1]=4,地址&a[0][0]+4
a[1][2]=5,地址&a[0][0]+5
分配存储空间时,系统把每3个数据作为一组,组名记a[0]、a[1],这两个值分别是每组第一个元素的地址,即a[0]=&a[0][0],a[1]=&a[1][0]。
所以:
a指向数组首元素的地址,a=&a[0][0];
a[0]代表第一组首元素地址,当然,a[0]也指向数组首元素的地址,a[0]=&a[0][0];
*a是对a取值,它取出的是a[0],当然=&a[0][0];
&a[0]指a[0]的地址,还是它自己,所以&a[0]=&a[0][0]。
所以,第一行个打印语句输出的5个内容都是一样的,所以,输出5个19ff0c。是a[0][0](元素0)的储存位置。
第二个打印语句输出的5个内容也是相同的,都是19ff18。它们是a[1][0](元素3)的存放位置,19ff0C+3×4=19ff0c+12=19ff0c+c=19ff18。
后面也是类似解释。
具体p1、p2、p3的使用,是前面定义了三个字符串,此处拿来使用。你可以直接把p1的内容"%x,%x,%x,%x,%x\n"拿来替换掉p1,就好理解了。
有什么问题请留言。
追问这个程序将指针p1放入输出里,是指针p1依次指向a,*a,a[0]还是有别的意思
*a是对a的取值,但a指向的数组首元素地址,那*a不应该取出地址的值0吗
追答p1只是一个字符数组,它的值是“%x,%x,%x,%x,%x\n”,没有任何其他意义。
如果不用p1,第一个输出语句你可以写成:
printf(“%x,%x,%x,%x,%x\n”,a,*a,a[0],&a[0],&a[0][0]);
p1的作用仅此而已。
p1永远也不会指向a,a[0]等等,也不需要p1执行它们。
另外,a是二维数组,相当于二级指针。a相当于二维数组的首地址(等于a[0][0]的地址)。*a是取得一维数组a[0]的首地址(也等于a[0][0]的地址)。
*a才是一级指针,对它取值**a才能得到a[0][0]的元素值0。