C语言实际参数的转换

  • C语言允许在(实际参数)与(形式参数)不匹配的情况下进行函数调用。如何转换实际参数与编译器在调用函数前是否遇到函数原型有关
    (1)若调用前编译器已经知道函数原型(这是通过函数声明实现的),那么每个实际参数都会被隐式地转换为相应的形式参数的类型,请看:
void Test(int a , int b); //函数声明 
int main(void)
{
	double a=1.0,b=2.0;
	Test(a,b);
	printf("%d\n",sizeof(a));	
	return 0;
}
void Test(int a, int b) 
{
	printf("%d\n",sizeof(a));
}//以下是输出结果:
4
8
--------------------------------
Process exited after 0.05654 seconds with return value 0
请按任意键继续. . .

(2)编译器在调用前没有遇到原型。编译器执行默认的实际参数提升,把float实际参数转化为double;把char和short实际参数转化为int,请看:

int main(void)
{
	float a=1.0,b=2.0;
	Test(a,b);
	return 0;
}
void Test(float a, float b) 
{
	printf("a=%f\n",a);
}
  • 这样一个程序,大家猜猜输出结构是什么?仔细看哦!
    如果你猜输出1.000000,那结果可能会让你大吃一惊!
a=0.000000
--------------------------------
Process exited after 0.04243 seconds with return value 0
请按任意键继续. . .
  • 不仅输出错误,而且伴随有编译器的[warning],编译器说“调用函数传递参数类型不匹配”,说明传入的不是float类型;还说“previous implicit declaration of Test was here(2行)”,也就是说,在调用函数时实现了隐式的定义。
    在这里插入图片描述
  • 那怎么知道隐式的定义转换成了double类型呢?请看:
int main(void)
{
	float a=1.0,b=2.0;
	Test(a,b);
	return 0;
}
void Test(double a, double b) //改成double便可以正确输出
{
	printf("a=%f\n",a);
}//以下是输出结果:
a=1.000000
--------------------------------
Process exited after 0.04994 seconds with return value 0
请按任意键继续. . .
  • 把函数定义的参数列表改为double类型,便可以正确输出了,说明的确转化为了double类型(用其他类型均不能正确输出,我们知道低精准度可由高精准度输出,高精准度不能由低精准度输出)。
  • char和short是一样的,可以自己动手试试,不过即使是int类型的值,也可以通过%c和%hd的格式输出,所以验证是否转换为Int比较困难,但是编译器的确报错了,说明的确是发生了隐式转换。
  • 综上所述,C语言支持的这种隐式转换非常危险,因为我们定义函数的参数列表时,一般会有非常明确的目的,发生隐式转换一般就意味着程序设计可能出现了纰漏,好在编译器会为这种隐式转换发出warning,但是不同的编译器可能不同,因此,我们提倡在函数被使用前一定要声明,保证编译器在调用函数之前就已经了解到了函数原型
  • 有上述思想,我们很容易知道,当参数列表为空时,我们应该给列表显示地添加一个void,这样就非常明确
补充:在C99中,使用函数前不提供该函数的声明和定义会被判定为错误。因此,本篇文章在C99环境下只有(1)有点实际意义,大家就当看个热闹吧。
  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值