C语言:二维数组和指针关系的分析(个人见解)

说明

在C语言程序的编写中,涉及到数组。一般情况我们都是利用数组的下标对数组中的元素进行操作。
如: 一维数组:a[1]=51 二维数组:a[1][1]=51
当深入分析,会发现数组和指针之间是有一定的关系的。很多地方很绕,导致很难去理解。
我结合程序,写出我自己的看法。大家来一起研究。

内容

1. 整形(int)

首先从整形开始。我们定义一个整形变量,并且读取他的结果和地址。

    int a = 10;
    printf("整形a的值:%d\n", a);
    printf("整形a的地址:%p\n", &a);
   	printf("整形a的值:%d\n", *(&a));

结果:

整形a的值:10
整形a的地址:007DF798
整形a的值:10

这很好理解,甚至我在第三句做了复杂操作:首先 a的地址,然后对该地址进行 解引用,同样可以得到a的值。
注意: 此时的变量名仅仅是一个int类型的变量。
其结构如下图:
整形关系

2.一维数组

我们开始讨论一维数组,char str[5]={"ABCD"};
首先先确定一位数组在内存中事怎么存储的。其结构图如下:
char
注意: 与整形不同,此时的变量名是一个指针,指向的是数组首元素的地址。
深入探讨: 这个str其实和真正的指针变量是稍有不同的。
一个指针变量:int * p = &a 其储存结构如下:

在这里插入图片描述
不同点:

  1. 对于指针变量,指针p有自己的内存地址,在其地址下 存放 了所指向 地址。
  2. 对于数组名,他自己的内存地址就是第一个元素的地址,对应的值也是一个元素的地址。

进行代码分析:

    printf("--------------char[]------------\n");
    char str[5] = { "ABCD" };
    printf("数组的值:%s\n",str);
    //partA
    printf("--------------PartA------------\n");
    printf("数组名str:%p\n", str);
    printf("数组名str取址:%p\n", &str);
    printf("数组名str取值:%c\n", *str);
    printf("数组名str取值:%s\n", *(&str));
    printf("--------------PartB------------\n");
    printf("数组名str[1]取址:%p\n", str+1);
    printf("数组名str[1]取址:%p\n", &str[1]);
    printf("数组名str[1]的值:%c\n", str[1]);
    printf("数组名str[1]的值:%c\n", *(str + 1));

结果:

--------------char[]------------
数组的值:ABCD
--------------PartA------------
数组名str:0099F7E0
数组名str取址:0099F7E0
数组名str取值:A
数组名str取值:ABCD
--------------PartB------------
数组名str[1]取址:0099F7E1
数组名str[1]取址:0099F7E1
数组名str[1]的值:B
数组名str[1]的值:B

分析:
partA部分:*(&str): 对str取址,其地址就是第一个元素的地址,然后再对它解引用,其值就是第一个元素的地址。
这点很混乱 ,我自己的理解就是,str如果看作是一个指针变量,它自身所在的内存地址,和他存的地址值是一样的。
partB部分:str[1]*(str+1) 是一样的!涉及c语言的语法糖。

3.二维数组

运用上面的思维,相对很容就对二维数组进行分析。
设定二维数组:char array[4][5];
其储存结构如下:
在这里插入图片描述
编写代码,对地址进行分析

    /*----------二维数组-----------*/
    printf("--------------二维------------\n");
    char array[4][5] = { "ABCD", "EFGH" , "IGKL","MNOP" };
    //PartA
    printf("--------------PartA------------\n");
    printf("二维数组array的地址:%p\n", array);
    printf("二维数组array的地址:%p\n", &array);
    printf("二维数组array的地址:%p\n", *array);
    //PartB
    printf("--------------PartB------------\n");
    printf("二维数组array[0]的地址:%p\n", array[0]);
    printf("二维数组array[0]的地址:%p\n", &array[0]);
    printf("--------------PartC------------\n");
    //PartC
    printf("二维数组array[1]的地址:%p\n", *(array+1));
    printf("二维数组array[1]的值:%c\n", **(array + 1));
    //PartD
    printf("--------------PartD------------\n");
    printf("二维数组array[0][1]的值:%c\n", *(array[0]+1));
    printf("二维数组array[1][3]的值:%c\n", *(*(array + 1)+3));

结果:

--------------二维------------
--------------PartA------------
二维数组array的地址:0059FD50
二维数组array的地址:0059FD50
二维数组array的地址:0059FD50
--------------PartB------------
二维数组array[0]的地址:0059FD50
二维数组array[0]的地址:0059FD50
--------------PartC------------
二维数组array[1]的地址:0059FD55
二维数组array[1]的值:E
--------------PartD------------
二维数组array[0][1]的值:B
二维数组array[1][3]的值:H

分析:
1、由于数组增加到了二维,数组的名称名称也变成了2级 array 和 array[]。
2、array通过一次解引用得到的是array[0]的地址,array[0]再经过一次解引用,才能得到array[0][0]的值。

结论

对与二维数组和指针之间的关系目前的理解就是这样。结论如下

  1. 数组的变量名不同于指针变量,它的地址(&)就是数组第一个元素的地址,它的解引用(*)的值也是第一个元素的地址。相当于指针变量自身地址和存储的地址变量的值是一样的。(我存着我自己)
  2. 对于一位数组,函数名解引用完事第一个元素的地址。而对于二维数组,函数名解引用完是函数名[ ]的地址,函数名[ ]再解引用后才是第一个元素的地址。
  3. 属于初学阶段,希望能有更深的理解。
  • 2
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值