最近在复习数组和指针的内容,同样也遇到了一些该内容的题,在此文梳理一下,也作为自己考研过程中的一段总结。本文IDE为VS2010,如果测试结果不同,请自行斟酌。
1.一维数组地址
这个是挺基础的概念就不过多解释,总结来说就是地址(1维地址的名字)按照数据类型所占的字节数为一个单位进行加减法。
#include <cstdio>
int main(){
int tArray[3] = {1, 2, 3};
printf("tArray:%d, tArray + 1:%d\n", tArray, tArray + 1);
return 0;
}
out.txt调试结果输出为
tArray:6158976, tArray + 1:6158980
2.二维,多维数组的地址加减法
网上有种说法是多维数组(包括二维)的名字仍是指向该数组的第一个数据地址,但是在VS2010证实是错的,其实多维数组的名字是指向以第二维到最后一维为一个单位的地址。
所以二维或者多维数组,其数组名字加减法的单位跨度是以后面几个维度的地址长度进行跳跃的。
int hArray[5][15];
printf("hArray:%d, hArray + 1:%d\n", hArray, hArray + 1);
输出
hArray:12581728, hArray + 1:12581788
3.数组地址加减法和取值[]
由1可以知道地址加减法就是根据字节数进行地址值加减,取得的仍是地址值,而取值[]就是从那个地址值去找对应的数据值,所以a[i]也可以表示为*(a + i)。 所以,在2的图片中,想要找第4条阿尔卑斯的第5颗糖(值),可以用a[3][4],(*(a+3))[4], *(*(a+3) + 4),而如果仅仅想取地址值,可以用a[3] + 4, *(a+3) + 4.
4.数组指针与地址
关于指针理解的一个小技巧是,可以把指针当做一个unsigned 的数值(地址值)看待
我们知道可以定义一维数组和一个简单的指针进行赋值和运算。
int kArray[3] = {1, 2, 3};
int *k = kArray;
而对于多维数组,对于多维的数组,指针定义的形式就需要发生变化,不然就通不过编译。
由阿尔卑斯图可以理解这个错误是,不能把指向一条阿尔卑斯的指针复制到单条阿尔卑斯数组的指向一颗糖的指针上去。
所以正确的做法是要匹配
int kArray[3][5] = {{1, 2, 3}};
int (*k)[5] = kArray;
int 和[5],就是告诉系统这个指针的加减法地址该加减多少。同样这个也是跟kArray的类型相匹配的。
对于多维数组,也可以推理出
int kArray[3][5][4][6] = {{1, 2, 3}};
int (*k)[5][4][6] = kArray;
5.地址,值,输出函数的关系
就printf举例,数值类型和字符类型的输出对于地址和值的内容是不同的,而对于字符串来说需要以地址作为输出。
char a[4][5] = {{'a','b','c','d','\0'},{'e','f','g','h','\0'},{'i','j','k','l','\0'},{'m','n','o','p','\0'}};
printf("a[3] + 1:%s\n", a[3] + 1);
输出
a[3] + 1:nop
可以看到输入的是‘n’字符的地址,输出的是从‘n’开始截止到‘\0’的字符串