给你下述C程序代码:
void exchange1(int para1,int para2) { int temp; temp = para1; para1 = para2; para2 = temp; } void exchange2(int *pInt1,int *pInt2) { int *temp = NULL; *temp = *pInt1; *pInt1 = *pInt2; *pInt2 = *temp; } void exchange3(int *pInt1,int *pInt2) { int *temp; temp = pInt1; pInt1 = pInt2; pInt2 = temp; } void exchange4(int *pInt1,int *pInt2) { int temp; temp = *pInt1; *pInt1 = *pInt2; *pInt2 = temp; } int main(void) { int para1 = 1, para2 = 2; exchange1(para1, para2); exchange2(¶1, ¶2); exchange3(¶1, ¶2); exchange4(¶1, ¶2); }
这几个函数里,哪几个函数可以实现main函数中的para1和para2的交换?
1、“己他”概念和“星指组合”概念来解题
这道C语言指针题看上去让人“眼花缭乱”,其实使用我提出的C语言指针“己他”概念和“星指组合”来解这道题是很简单的。有关C语言指针的“己他”概念和“星指组合”概念在我的专栏:
的第九章和第十章有详细的阐述,有兴趣的同学可以阅读这两章:
这道C语言指针试题就会用到“己他”概念中的“己值”、“他值”和“星指组合”的概念!
简单来说,这些概念的意思分别如下:
1.1 “己X”概念
“己X”分为己型、己址和己值。
“己型”:就是C语言指针自己的类型;
“己址”:就是C语言指针自己的地址;
“己值”:就是C语言指针自己的数据值;
1.2 “他X”概念
“他X”概念分为他型、他址和他值。
“他型”:就是C语言指针指向的对象的类型;
“他址”:就是C语言指针指向的对象的地址;
“他值”:就是C语言指针指向的对象的数据值;
1.3 “星指组合”概念
“星指组合”就是“星号”+“指针变量”的组合,这种组合的意思就是获取指针变量的他值!
2、C程序代码
我来把这道C语言指针题扩展成一段C程序代码,如下:
有四个函数,分别试图交换main函数中的两个参数,我们来看看运行结果:
3、C程序代码分析
3.1 分析1
在C程序代码的exchange2函数中,参数指针变量pInt1的己值是int变量para1的地址,参数指针变量pInt2的己值是int变量para2的地址。我们来看13行到15行:
第13行:*temp = *pInt1; 第14行: *pInt1 = *pInt2; 第15行: *pInt2 = *temp;
第13行,我们通过“星指组合”拿到了指针变量pInt1的他值和指针变量temp的他值,并且试图把pInt1的他值给temp的他值!
要知道指针变量temp刚开始的己值是NULL,这是空值的意思,请问此时temp的他值是什么呢?答案是:内存地址是NULL的这块地皮上的数据值,至于是什么数据值,没人知道,也许是一个非常重要的数据值。那么你想用pInt1的他值来覆盖掉这个数据值,操作系统会答应吗?当然不会,所以在运行的时候会给你一个大大的“运行时”错误!
第14行代码没问题的,这是通过“星指组合”拿到了指针变量pInt2的他值和指针变量pInt1的他值,并且试图把pInt2的他值给pInt1的他值,这是可以的!
第15行代码没问题的,这是通过“星指组合”拿到了指针变量temp的他值和指针变量pInt2的他值,并且试图把temp的他值给pInt2的他值,这是可以的!
你看,在main函数中我也把exchange2函数给注释掉了,因为运行时这个函数肯定运行报错!
3.2 分析2
在C程序代码的exchange3函数中,参数指针变量pInt1的己值是int变量para1的地址,参数指针变量pInt2的己值是int变量para2的地址。我们来看20行到22行:
第20行:temp = pInt1; 第21行: pInt1 = pInt2; 第22行: pInt2 = temp;
1)、第20行,我们把指针变量pInt1的己值给了指针变量temp的己值,此时pInt1的己值和temp的己值都是para1的地址;
2)、第21行,我们把指针变量pInt2的己值给了指针变量pInt1的己值,此时pInt1的己值和pInt2的己值都是para2的地址;
3)、第22行,我们把指针变量temp的己值给了指针变量pInt2的己值,此时pInt2的己值和temp的己值都是para1的地址;
经过这三步,最后的结果就是参数指针变量pInt1的己值变成了para2的地址,而参数指针变量pInt2的己值变成了para2的地址,仅仅是pInt1和pInt2的己值发生交换,而para1和para2的值并没有发生交换。而要实现main函数中para1和para2的交换,必须得是pInt1和pInt2的他值发生交换才行。
3.3 分析3
在C程序代码的exchange4函数中,参数指针变量pInt1的己值是int变量para1的地址,参数指针变量pInt2的己值是int变量para2的地址。我们来看27行到29行:
第27行:temp = *pInt1; 第28行: *pInt1 = *pInt2; 第29行: *pInt2 = temp;
1)、第27行,我们通过“星指组合”拿到了指针变量pInt1的他值,也就是para1的值:1,并且给了int变量temp。此时指针变量pInt1的他值是1,temp的值也是1;
2)、第28行,我们通过“星指组合”拿到了指针变量pInt1的他值,也就是para1的值:1,pInt2的他值,也就是para2的值:2,并且把pInt2的他值“2”给了pInt1的他值,此时指针变量pInt1的他值,也就是para1的值就变成了2,pInt2的他值,也就是para2的值还是2;
3)、第29行,我们把temp的值1给了通过“星指组合”拿到的指针变量pInt2的他值,也就是para2的值,此时指针变量pInt2的他值就变成1,也就是para2的值变成1;
所以你看exchange4函数中,pInt1和pInt2的他值发生交换,才实现了main函数中para1和para2的交换。而在exchange2和exchange3中均未做到这一点。
这道C语言指针试题看上去难,其实也是绕不开我提出的“己他”概念和“星指组合”概念,所以我一直跟同学们说“C语言指针就是个纸老虎”!