【C语言】指针

指针

指针:指针是一个值为内存地址的变量(或数据对象)。

一、指针的声明

 

//示例
int *pi;    //pi是指向int类型变量的指针
char *pc;   // pi是指向char类型变量的指针
float *pf;    // pi是指向float类型变量的指针

 

 在定义时,以下几种写法效果相同

int *p = NULL;
int* p = NULL;
int * p = NULL;

 

注意,指针的值虽然是地址,指针本身也是有自己的地址和大小的。在计算机中,指针的大小为8字节,在stm32中,为4字节。

二、指针的赋值与解引用

int num=2;
int *p;
p=#
printf("%d",*p);//结果输出为2

赋值要符合指针的定义,要向指针赋一个地址,如果定义时未赋值,形成野指针(野指针就是指针指向的位置是不可知的(随机的、不正确的、没有明确限制的)指针变量在定义时如果未初始化,其值是随机的,指针变量的值是别的变量的地址,意味着指针指向了一个地址是不确定的变量,此时去解引用就是去访问了一个不确定的地址,所以结果是不可知的)。

野指针因为指向地址是不可预知的,所以有3种情况:第一种是指向不可访问(操作系统不允许访问的敏感地址,譬如内核空间)的地址,结果是触发段错误,这种算是最好的情况了;第二种是指向一个可用的、而且没什么特别意义的空间(譬如我们曾经使用过但是已经不用的栈空间或堆空间),这时候程序运行不会出错,也不会对当前程序造成损害,这种情况下会掩盖你的程序错误,让你以为程序没问题,其实是有问题的;第三种情况就是指向了一个可用的空间,而且这个空间其实在程序中正在被使用(譬如说是程序的一个变量x),那么野指针的解引用就会刚好修改这个变量x的值,导致这个变量莫名其妙的被改变,程序出现离奇的错误。一般最终都会导致程序崩溃,或者数据被损害。这种危害是最大的。

为避免出现野指针导致的错误,常规的做法是:
第一点:定义指针时,同时初始化为NULL
第二点:在指针解引用之前,先去判断这个指针是不是NULL
第三点:指针使用完之后,将其赋值为NULL
第四点:在指针使用之前,将其赋值绑定给一个可用地址空间

 

关于NULL

#ifdef _cplusplus            // 定义这个符号就表示当前是C++环境
#define NULL 0                // 在C++中NULL就是0
#else
#define NULL (void *)0        // 在C中NULL是强制类型转换为void *的0
#endif

 

三、指针的操作

int arr[5]={1,2,3,4,5};//数组名本身为一个指针

取址操作: &arr
自加自减,与整数相加减: arr++;  arr--;  arr+=2;  

            在本例中,指针与整数相加减时,它所指向的地址增加或减少整数个int的大小,如arr+=2储存ar[2]的地址

指针求差:相同类型指针之间可以相减,差值为整数个指针类型大小

四、指针与const

const int *p;    //const修饰p指向的变量
int const *p;    //const修饰p指向的变量
int * const p;    //const修饰p指针
const int * const p;  //const两者都修饰

 

使用const可以保护数组的数据不被修改,相比于#define,const的用法更加灵活

const int days[3]={20,13,5};

此后数组的元素不能被修改,否则会报错

 

如果函数这样定义,那这个函数将不能改变要传入的数组

void show_arr (const double *p,int n);

 

posted @ 2019-01-16 18:30  横秋  阅读(338)  评论(0编辑  收藏  举报