C语言指针基本概念与理解
欢迎关注AWP资讯
指针是C/C++编程语言中的重要概念,但是对于初级程序员来说,指针是个比较难理解的概念,下面就从指针的概念入手,一点点解密指针。学习并理解指针首先已经具备基本的编程知识,能够编写C程序,对于变量知道如何定义并进行运算。
变量在内存中的分配
要理解指针首先要对不同数据类型的变量在内存中是如何分配存储的要有个认识,指针的本质也是变量。计算机中的内存是如何分布的,从下面的表中开始入手,下表表示一段内存,从0地址开始,每个地址代表一个字节,表中的0x1001~0x1009表示的这一段地址,其他的地址省略
我们定义两个变量
int a;
char c;
这两个变量在内存中所占的内存大小分别是多少呢?
int所占大小为4byte
char所占大小为1byte
变量所占用的地址大小也是一样,假设整形变量int a所占的地址为0x1004~0x1007,字符型变量char c所占的地址为0x1009在内存中的示意如下,变量a的起始地址为0x1004,当在程序中又声明了一个字符变量c时,计算机将开辟一个字节的空闲内存存放变量c,变量c的起始地址为0x1009
当我们给定义的变量赋值时,变量对应地址中的值就会随之改变,将a赋值为5如:
int a;
char c;
a = 5;
当前a地址中的值就为5,程序在执行运算,比如此时变量a的值需要改变,出现一个a++的运算,如:
int a;
char c;
a = 5;
a++;
程序运行会找到变量a对应的地址空间,修改存放的值,自增1,a的值变为6,那么在代表a的这块内存中的值就是6了。
指针变量的引入和应用
有了以上变量在内存中的理解,我们可以思考一下在程序中我们是否可以通过内存地址进行操作呢?指针在这时就可以登场了,指针是一个变量,它存放着另外一个变量的地址,首先我们假设在内存中有一个整形变量a = 4,另外一个变量是指针p,p存放着变量a的地址,那么我们就可以通过操作p来访问变量a,下面是指针的语法和内存示意。
int a = 4;
int *p;
P = &a;
此时我们也可以定义一个变量b,使指针p指向变量b的地址,比如变量b的地址为0x208,p = &b;p的值为0x208。
对此我们可以用一段代码进行理解,如下为代码和打印结果。
#include <stdio.h>
int main()
{
int a = 4;//定义整形变量a并赋值为4
int *p;//定义指针变量p;
p = &a;//将a的地址赋值给指针p
printf("p = %d\n",p);//将打印出a的地址
printf("*p = %d\n",*p);//打印出a的值a = 4
printf("&a = %d\n",&a);//打印出a的地址
printf("a = %d\n",a);//打印出a的值 a = 4
return 0;
}
这里有个概念是解引用,利用解引用可以操作其他变量的值,*p表示p所指向变量地址的值,p是所指向变量的地址,通过 *p来修改变量的值比如:
#include <stdio.h>
int main()
{
int a = 4;
int *p;
p = &a;
*p = 10;//修改变量a的值
printf("p = %d\n",p);
printf("*p = %d\n",*p);
printf("&a = %d\n",&a);
printf("a = %d\n",a);
return 0;
}
我们得到的结果就是通过操作指针变量p,完成了对变量a的修改,结果如下:
我们再来看一段关于指针操作的代码
int main()
{
int a;
int b;
int *p;
p = &a;
printf("*p = %d\n",*p);//未初始化变量a,是个随机值
*p = 10;
printf("p = %d\n",p);
printf("*p = %d\n",*p);
printf("&a = %d\n",&a);
printf("a = %d\n",a);
b = 20;
*p = b;
printf("*p = %d\n",*p);//*p = 20,这里只是将b的值赋值给*p,p指向的地址还是a
printf("p = %d\n",p);//p=&a,打印出来还是a的地址
printf("a = %d\n",a);//a的值被修改为20
return 0;
}
如果上面的代码需要指针指向变量b的地址,需要将代码写为p=&b;这样p的值就是变量b的地址值,指针变量的定义写法还有如下方式:
int a = 5;
int *p = &a;//同时声明和初始化一个变量
指针变量的运算
先看一段代码,猜想一下打印输出的值
#include <stdio.h>
int main()
{
int a = 1;
int *p;
p = &a;
printf("p = %d\n",p);
printf("p+1 = %d\n",p+1);
return 0;
}
根据上面一节的理解可以知道,p的值为变量a的地址值,但是p+1这里的值是多少呢?首先分析p是一个指针变量,里面的值是a的地址,得到的是下一个整形数据的地址,也就是在p的值的基础上增加4个字节,如果p的地址值是0x1001,那么p+1的值为0x1005将上面的代码打印出来,看看是不是p+1的值比p大4
我们继续考虑*(p+1)这种运算的结果是多少,这个表达的意思就是下一个地址的值,但是这里的值是未知的(未初始化的),使用起来就比较危险,所以使用指针需要小心,指针可以指向任何地址,一不小心可能把系统搞崩溃。最后我们来看一段代码,体会一下指针运算的应用。
#include <stdio.h>
int main()
{
int a = 1;
int *p;
p = &a;
printf("p = %d\n",p);
printf("p+1 = %d\n",p+1);
printf("*(p+1) = %d\n",*(p+1));
printf("*p+1 = %d\n",*p+1);
return 0;
}
运行结果: