默认的说法促销活动在C功能的电话
-
12-09-2019 - |
题
设置
我有几个问题,关于默认的说法促销活动时调用一个功能。这部分6.5.2.2"功能要求"第6、7和8 C99标准(pdf) (强调是后加入和闯入清单,为了便于阅读):
第6段
- 如果表达,表示在所谓的功能有一个类型的 不包括一个原型, ,整数的促销活动是执行在每个参数和参数,有型
float
促进来double
.这些被称为 默认的说法促销活动.- 如果数量的参数并不相等的数量的参数,行为是不确定的。
- 如果功能定义的类型 包括一个原型, 和任的原型结束的省略号(
, ...
)或类型的争论之后,促进不兼容类型的参数,行为是不确定的。- 如果功能定义的类型 不包括一个原型, 和类型的争论之后,促进不符合这些参数之后促进,行为不确定,除以下情况:
- 一个推动类型是一个签署整数类型,其他促进类型是相对应的符号的整数类型和价值是可表示在这两种类型;
- 这两种类型都指向合格或不合格的版本的文字类型或
void
.
第7段
- 如果表达,表示在所谓的功能有一个类型的 不包括一个原型, ,该论点是隐含地转换,因为如果通过分配,到的类型相应的参数,考虑每个参数的类型以不合格的版本,其中宣布类型。
- 省略号表示法在功能原型声明的原因的论点类型转换为停止后的最后声明的参数。 默认的说法促销活动是执行后的论点。
第8段
- 没有其他进行转换隐含;特别是,数量和类型的论点是不相比,那些参数的一个函数的定义 不包括功能原型的声明.
什么我知道
- 的 默认的说法促销活动 都
char
和short
要int
/unsigned int
和float
要double
- 《任择参数的可变职能(喜欢
printf
)是受到默认的说法促销活动
为了记录在案,我的理解的 功能原型 是这样的:
void func(int a, char b, float c); // Function prototype
void func(int a, char b, float c) { /* ... */ } // Function definition
的问题
我有一个很艰难的时期groking所有这一切。这里有一些问题我有:
- 做原型并非原型职能'的行为真的很不同很多,例如关于默认的促销活动和隐性转换?
- 当做默认的说法促销活动发生?它是永远?或者只是在特殊情况(如与可变的功能的)?它不会取决于是否有一个功能原型?
解决方案
投赞成票AProgrammer是答案—这些是真正的货物。
对于那些你们都想知道 为什么 事情是这样的:在黑暗的中世纪之前,1988年,有没有这样的东西作为一个功能原型的经典"K&R"C和默认的说法促销活动提起的,因为(a)基本上有"免费"的,因为它费用没有更多的把字节的一个登记册,而不是把单词的一个登记册,以及(b)减少潜在的错误。在参数通过。第二个原因从来没有完全切开它,这就是为什么引进的功能原型在ANSI C的一个最重要的改变没有在C语言。
作为时,默认的促销活动踢: 默认的说法促销活动中使用的确切时预期类型的说法是 未知, 这是说的时候有没有原型或当时的说法是可变.
其他提示
(不可变)参数的功能原型转换为相应的类型,这可以char,短,浮动。
参数的功能没有原型和可变的参数都受到默认的说法促销活动。
如果定义的一个函数的一个原型,并使用它没有原型或反之亦然,并且它具有参数的类型炭,短期或浮动,你很可能会有问题。你会有同样的问题可变的功能的,如果推广类型的不匹配时使用的阅读的论点列表。
实例1:问题在限定的一个函数的一个原型,并使用它。
定义。c
void f(char c)
{
printf("%c", c);
}
使用。c
void f();
int main()
{
f('x');
}
可能会失败,因为一个int将通过和功能期待一个红点鲑。
实例2:问题在限定的一个功能没有原型和使用一个。
定义。c
void f(c)
char c;
{
printf("%c", c);
}
(这是一种定义是非常老式)
使用。c
void f(char c);
int main()
{
f('x');
}
可能会失败,因为一个int是预期的,但char会通过。
注:你会说法,所有职能的标准图书馆的类型,其结果从默认的促销活动。所以他们并没有引起问题在过渡时原型,增加了。
你的混乱来源于一个非常微小的误解的术语这两种声明和定义可以包括原型(或不):
void func(int a, char b, float c);
这是一个功能 宣言 这包括一个原型。
void func(int a, char b, float c) { /* ... */ }
这是一个功能 定义 这包括一个原型。
"原型"和"非原型",都是属性的一个函数 类型, 和这两种声明和定义介绍的类型功能。
所以你可以有一个《宣言》没有一个原型:
void func();
或者你可以有一个定义没有一个原型(K&R C):
void func(a, b, c)
int a;
char b;
float c;
{ /* ... */ }