C语言中的数组和指针
先看段代码
1 int arr[] = {344,243,55,6,10};
2 for (int i = 0; i < 5; i++)
3 printf("%p\n", &arr[i]);
数组arr
的每个元素的地址,依次被打印,运行结果如下
10x7fff5c45b590
20x7fff5c45b594
30x7fff5c45b598
40x7fff5c45b59c
50x7fff5c45b5a0
每个地址相差4,正好是一个int
型整数占的字节数。
问题来了,是不是每个元素的地址,正好相差元素数据类型所占的字节数呢?
答案:是的。
再来看段代码验证一下
1 char arr[] = "abcd";
2 for (int i = 0; i < 4; i++)
3 printf("%p\n", &arr[i]);
4
5 for (int i = 0; i < 14; i++)
6 printf("-");
7
8 printf("\n");
9
10 double arr2[] = {10.000, 13.2, 15.6, 123.678};
11 for (int i = 0; i < 4; i++)
12 printf("%p\n", &arr2[i]);
运行结果
10x7fff5c2c8577
20x7fff5c2c8578
30x7fff5c2c8579
40x7fff5c2c857a
50x7fff5c2c857b
6--------------
70x7fff5c2c8580
80x7fff5c2c8588
90x7fff5c2c8590
100x7fff5c2c8598
110x7fff5c2c85a0
字符串可被看作字符数组,每个字符占1个字节,地址相差1。
双精度型数组,每个元素占8个字节,地址相差8。
可见,上面的结论是对的。
地址
到底指什么呢?
依据这里的描述
The address of a variable is the address of its first byte of storage that it occupies
每个变量可能会占若干字节,变量地址
指的是它所占的第一个字节的地址。
所以,当我们打印数组每个元素的地址时,实际上是在打印每个元素所占的第一个字节的地址。
说到地址,自然想到指针,于是我们想知道
究竟啥是指针?
通常所说的指针是指指针变量
,这种变量的值是十六进制的地址,而该地址可能属于另一个变量。所以,通过指针变量可以取到它所存的地址所属的变量(或许没有变量)的值。举个例子
1 int a = 100;
2 int *p;
3 p = &a;
4
5 printf("%p\n", p);
6 printf("%d\n", *p);
p
是指针变量,它的值是变量a
的地址,通过*p
获取到a
的值。运行结果
10x7fff5065d5a8
2100
再回到数组,做个实验
1 int arr[] = {344,243,55,6,10};
2 printf("%p\n", arr);
3 printf("%p\n", &arr[0]);
运行结果
10x7fff5d0d0590
20x7fff5d0d0590
可见,数组名arr
本身可被看作一个指针变量
,它保存的正是第一个元素的地址。在c语言中,arr+1
表示指针指向下一个元素的地址,所以,下面的等式是成立的
1arr+n = &(arr[n])
2*(arr+n) = arr[n]
综上所描述,可得结论
数组名可看作指向数组第一个元素的指针,指针加n,则指向数组第n个元素