首页 > 代码库 > 指针知识梳理2-指针与一维数组

指针知识梳理2-指针与一维数组

一、一维数组复习

数组的本质是连续的内存,我们可以通过一下代码验证。

int main()
{
	int a[10];
	int  i;
	for(i = 0;i<10;i++)
	{
		printf("%p\n",&a[i]);
	}

}
打印出每个元素的地址,会发现地址间隔是4 ,这个间隔刚好等于sizeof(int)。

那么如果知道了a[0]的地址,我们就可以通过地址的加减算出a[i]的地址,然后访问a[i];

二、通过指针访问一维数组

指针能够访问一维数组的两个前提是:

1、内存连续,地址相邻。

2、指针加减的规则。

对于 

int *p;

int  a[10];

如果 p = &a[0],p存储的是a[0]的地址,p+i就存储的是a[i]的地址,那么 *(p+i)就是访问a[i]的内存。

写代码验证如下:

#include <stdio.h>
int main()
{
	int i = 0;
	int a[10];
	p = &a[0];
	for(i = 0;i<10;i++)
	{
		*(p+i) = i;
	}
	for(i = 0;i<10;i++)
	{
		printf("%d\n",a[i]);
	}
	
	return 0;
}


也可以通过指针的累加 p++;

p++  本质是 p = p+1;

#include <stdio.h>
int main()
{
	int i = 0;
	int a[5];
	p = &a[0];
	for(i = 0;i<5;i++)
	{
		*p = i;
		p++;
	}
	for(i = 0;i<5;i++)
	{
		printf("%d\n",a[i]);
	}
	
	return 0;
}

画内存图如下

p++以后


在p++



三、语法上的一些规则

1、数组名

int  a[10];
int *p;
p = a;
当写出第三行等式的时候,这时候数组名代表的是 a[0]的地址,int 变量的地址为 int*,这只是语法的规则,记住这种情况就可以了。

因此可以写出以下代码:

#include <stdio.h>
int main()
{
	int i = 0;
	int a[10];
	p = a; //与p = &a[0]等效。
	for(i = 0;i<10;i++)
	{
		*(p+i) = i;
	}
	for(i = 0;i<10;i++)
	{
		printf("%d\n",a[i]);
	}
	
	return 0;
}

2、语法公式 *(p+i)  等效 p[i]

这个公式也只需要记住就可以了,其实数组的访问也是算出地址读写内存。

因此我们可以有多种方法访问数组

#include <stdio.h>
int main()
{
	int i = 0;
	int a[10];
	p = &a[0];
	for(i = 0;i<10;i++)
	{
		*(p+i) = i;
		//*(a+i) = i;
		//p[i] = i;
		//a[i] = i;
	}
	for(i = 0;i<10;i++)
	{
		printf("%d\n",a[i]);
	}
	
	return 0;
}

3、注意事项

注意 当把数组名a 当做a[0]的地址来看的时候,这是一个地址常量,只是一个值,因此不能用写出 a++.

p++,的原因是p是个变量,p++ 等于 p = p+1,这是在给变量赋值。