关于C语言中函数参数传递问题的探讨

时间:2022-06-22 12:41:07

关于C语言中函数参数传递问题的探讨

摘要:在C语言中,函数是实现程序模块化设计思想的手段。函数在调用过程中常常存在着实参和形参之间的数据传递。文章阐述了调用函数的过程中实参和形参之间数据传递的实质和属性,即值传递和单向性。

关键词:函数;形参;实参;数据传递

中图分类号:TP312文献标识码:A 文章编号:1009-3044(2007)17-31457-01

Analysis of Data Transferring from Actual Argument to Formal Argument in C Language Function Calling

LU Xiang-ning, LI Xiao-mei

(Hainan Software Professional Institute, Qionghai 571400,China)

Abstract: C's design philosophy is to use functions as building blocks. When a function is called, value of the actual argument is assigned to the variable known as the formal argument. This paper presents that the essence of data transferring from actual argument to formal parameter is value delivery and one-way.

Key words: functions; formal parameters; actual arguments; data transferring

1 引言

在C语言教学过程中,我发现有很多初学者对函数调用过程中实参和形参之间的数据传递问题理解不够透彻,尤其是指针做函数参数时,常常有许多误解。有这样一个程序:

#include

main()

{

void swap(int *p1,int *p2);

int a,b;

int *point1,*point2;

clrscr();

scanf("%d,%d",&a,&b);

point1=&a;point2=&b;

if(a

printf("a=%d,b=%d\n ",a,b);

printf("max=%d,min=%d\n ",*point1,*point2);

}

void swap(int *p1,int *p2)

{

int *temp;

temp=p1;

p1=p2;

p2=temp;

}

编程者的目的很明显,即编写用户自定义函数void swap(int *p1,int *p2),并以整型指针作为参数,在main()函数中调用这一函数来实现两个整型数据a和b的值的互换。但这个函数能否实现两个数值的交换呢?下面我们对其进行分析。

2 函数调用过程分析

在前面这一程序的main()函数中,整型指针变量point1、point2分别指向整型变量a、b,即point1 和point2的值分别为变量a和b的地址。在调用函数swap()时实参(point1,point2)将各自的“值”传递给形参(p1,p2) 。如图1所示(图中虚线箭头表示数据的传递方向,实线箭头表示指向),由于point1 和point2的值分别为变量a和b的地址,所以p1和p2也分别得到变量a和b的地址,即p1和p2也分别指向变量a和b。

图1 实参向形参进行“值”的传递

实参向形参进行“值”的传递之后,执行swap()函数的函数体部分,当执行语句“temp=p1;” 后,将p1的值(主函数中整形变量a的地址)赋给指针变量temp,这时temp也指向了变量a,如图2所示。

图2 执行赋值语句temp=p1;后

执行赋值语句“p1=p2;”,将p2的值(主函数中整形变量b的地址)赋给p1,这时p1不再指向变量a,而指向了变量b,如图3所示,temp和p2的指向不变。

图3 执行赋值语句p1=p2,后

最后执行赋值语句“p2=temp;”,将temp的值(主函数中整形变量a的地址)赋给p2,这时p2的值发生改变,不再指向变量b,而指向变量a。如图4所示。

由上述讨论可以看出,编程者调用swap()函数,仅仅改变了形参变量p1和p2的值,即改变了p1和p2的指向,而这一过程中实参变量point1 和point2并没有指向。swap()函数调用结束后,形参所占内存单元被释放,形参变量p1和p2以及局部指针变量temp消亡。因此,该程序调用swap()函数的执行结果就是改变了通过中间指针变量temp交换了两个形参变量p1和p2的指向,对main()函数没有起到任何作用。

3 函数的改正及问题分析

前例中,调用swap()函数虽然不能改变实参指针变量point1 和point2的值(即它们的指向),但是我们可以改变point1 和point2所指向的内存单元当中的值,即改变整型变量a、b的值。对swap()函数做如下修改:

void swap1(int *p1,int *p2)

{ int temp;

temp=*p1;

*p1=*p2;

*p2=tem}

分析修改后的函数swap1()可知,在函数swap1()调用执行过程中,不仅没能改变实参指针变量point1 和point2的指向,形参指针变量p1和p2的指向也一直没有改变,只是交换了是p1和p2指向的内存单元中的值,即使a、b值互换。

这样以来,就实现了函数调用的功能,达到了编程者的目的。

然而,也有很多人将swap()函数修改为如下形式:

void swap2(int *p1,int *p2)

{ int * temp;

*temp=*p1;

*p1=*p2;

*p2=*tem}

函数swap2()中,编程者以整型指针变量temp为中间变量,交换p1和p2所指向的内存单元中的值,是否能达到这个目的呢?

启动TUBOR C编译环境中,如前例在主函数中对swap2()函数进行调用,编译时 “*temp=*p1;” 语句出现警告,忽略这个警告,运行程序,并输入5,9按回车键,运行结果如图5。

显然,编程者的目的没有达到,执行swap2()函数的过程中,指针变量temp和p1指向了同一个内存单元,并将p2所指向的内存单元中的值赋给p1所指向的内存单元,即将main()函数中变量b的值赋给变量a,因而出现了图示结果。

函数swap2()中问题出现在语句“*temp=*p1;”,对指针变量temp的这种使用方式存在很大的冒险性。由于指针变量temp并没有确定的地址值,所以temp的指向是不可预测的,对*temp赋值可能会造成重要数据的丢失,应避免指针变量的这种使用方式。

4 结论

通过这个例子,本文浅析了函数调用过程中实参与形参之间数据传递的实质,即“值传递”,就好像是实参把自身的数值拷贝了一份给形参,这种“值传递”是单向的,即由实参传递给形参,形参无法改变实参的值。笔者认为这种提法不仅有失准确性,还给初学者造成了概念上的混淆,误认为传递的是实参变量的地址。初学者在学习C语言过程中,往往“谈指针色变”,理解指针做函数参数的情况更是难于上青天,本文结合实例,阐述了函数调用过程中实参对形参的“单向值传递”性,希望对广大初学者有所帮助。

参考文献:

[1]谭浩强.C程序设计[M] .北京:清华大学出版社,2000.186-189.

[2]陈家骏.程序设计教程用C++语言编程[M]. 北京:机械工业出版社,2004.155-160.

[3]Herbert Schildt,著.戴健鹏,译.C语言大全(第2版)[M]. 北京:电子工业出版社,1994.120-125.

注:本文中所涉及到的图表、注解、公式等内容请以PDF格式阅读原文。

本文为全文原貌 未安装PDF浏览器用户请先下载安装 原版全文

上一篇:高职电子商务专业面向就业培养模式改革思考 下一篇:一种基于Linux的flash文件系统存储策略