C语言指针与二维数组

#include<stdio.h>
int main(){
    int array[4][3] = {{1,2,3},{4,5,6},{7,8,9},{10,11,12}};
    int (*p)[3] = NULL;
    p = array;  // p is same as array,the use of p is same as array.
                //so p is the two-devision pointer same as array
    int *p1 = &array[0][0]; //p1 is the one-devision pointer
    int *p2 = array[0];
    //int **p3 = array;  this is wrong. the array's kind is int(*)[3]
    //but p3 is int**
    printf("%d  ",*array[0]);//out:1
    //(*p)[n]  think array is the one-devsion array
    //so (*p) is the header pointer of the one-devision array
    //so (*p)[1],(*p)[2]......(*p)[i] is right
    printf("%d  ",(*p)[0]);//out:1
    printf("%d  ",(*p)[1]);//out:2
    printf("%d  ",(*p)[2]);//out:3
    printf("(*p)[3]:%d  ",(*p)[3]);//out:4
    printf("(*p)[4]:%d  ",(*p)[4]);//out:5
    printf("(*p)[5]:%d  ",(*p)[5]);//out:6


    //think p is same totaly as array
    //*p pointing the zero row
    //*(p+1) pointing the one row
    //*(p+2) pointing the two row
    //*(p+3) pointing the three row
    //and array is four rows, so *(p+4) is overflow
    printf("%d  ",(*(p+1))[0]);   //out:4
    printf("%d  ",(*(p+2))[0]);   //out:7
    printf("%d  ",*(p+3)[0]);   //out:10
    printf("%d  ",*(p+3)[1]);   //overflow
    printf("%d  ",(*(p+3))[1]);   //11
    printf("%d  ",(*(array+3))[1]);//11
    printf("%d  ",*(array+3)[1]);//overflow
    printf("*(array+3)[0]: %d  ",*(array+3)[0]); //10
    printf("*(array+3)[1]: %d \n ",*(array+3)[1]); //overflow
    printf("%d  \n",*(*(p+3)+1));                   //out:11 
    printf("*(array[3*3+1]):%d  \n",*(array[3*3+1])); //overflow
    printf("*array[3*3+1]:%d  \n",*array[3*3+1]); //overflow
    //printf("*array[3*3+1]:%d  ",**array[3*3+1]); // is wrong **array[3*3+1]
    printf("%d  \n",*p[3*3+1]);  //overflow
    printf("*(array[3]+1):%d  \n",*(array[3]+1));  //11
     
    printf("%d \n ",*(p+4)[0]);   //overflow






   /*all below is wrong. p1 is the pointer pointing array[0][0]
    *  pi++ pointing array[0][1] and so on .the adder is sizeof(int)
    *
    printf("%d  ",(*p1)[0]);//out:1
    printf("%d  ",(*p1)[1]);//out:2
    printf("%d  ",(*p1)[2]);//out:3
    printf("(*p1)[3]:%d  ",(*p1)[3]);//out:4
    printf("(*p1)[4]:%d  ",(*p1)[4]);//out:5
    printf("(*p1)[5]:%d  ",(*p1)[5]);//out:6
    printf("%d  ",*(p1+1)[0]);   //out:4
    printf("%d  ",*(p1+2)[0]);   //out:7
    printf("%d  ",*(p1+3)[0]);   //out:10
    */
   int i = 0;
   for(i;i<12;i++){
        printf("%d  ",*(p1+i));       
    }
    printf("\n");






    // for p2=array[0]
    printf("%d  ",*p2);//1
    printf("%d  ",*p2+10); //11 
    printf("%d  ",*(p2+1));//2
    printf("%d  ",*(p2+2));//3
    printf("%d  ",*(p2+3));//4
    printf("%d  ",*(p2+4));//5
    printf("%d  ",*(p2+5));//6
    printf("%d  ",*(p2+6));//7
    printf("%d  ", *p2++); //1
    printf("%d  ",*p2);



     
}


对于二维数组用指针只能是上述p和p1和p2的用法,p3的赋值方法是错误的。

访问二维数组array[i][j]的方法有3种:*(array[i]+j)  array[i][j]  *(*(array+i)+j)

当int (*p)[3]=array时,p和array是一样的,都是行指针,则在行指针进行加法运算时,是行间的移动,例如array+i 和p+i,是跨行的移动

int *p1=&array[0][0] 此时p1是一维指针,则现在将二维数组看作一个一维数组,然后p1的移位操作来进行逐个元素进行访问。

p2同p1


还要注意的是:int *a[3] 说明的先后顺序是:p-->[3]-->*-->int  先说明数组,再说明指针;这是一个指针数组(指针数组,数组存储的是指针,将在下一篇文章中讲解)

所以上面代码中,如下:

printf("%d  ",*(p+3)[1]);   //overflow
printf("%d  ",(*(p+3))[1]);   //11
printf("%d  ",(*(array+3))[1]);//11
printf("%d  ",*(array+3)[1]);//overflow
要用(*(array+3))[1])这样的形式,用括号将*运算括起来先进行运算,(*(array+3)):表示{10,11,12}这个数组的首地址,再用[]操作来根据脚标进行取值。


printf("*array[3*3+1]:%d  \n",*array[3*3+1]); //overflow

这样的访问是错误的,因为array是行指针,所以array[3*3+1]已经越界了




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值