【发布时间】:2017-03-22 21:23:37
【问题描述】:
考虑这个函数声明和定义的例子(在同一个翻译单元中):
inline static int foo(int x);
...
int foo(int x)
{
return x+1;
}
我知道类型需要匹配,但是其他关键字和限定符呢? inline static 应该在这两种情况下吗?还是只是声明?
我可以使用 C 标准的哪个部分或哪个编码指南来证明答案的合理性?
【问题讨论】:
考虑这个函数声明和定义的例子(在同一个翻译单元中):
inline static int foo(int x);
...
int foo(int x)
{
return x+1;
}
我知道类型需要匹配,但是其他关键字和限定符呢? inline static 应该在这两种情况下吗?还是只是声明?
我可以使用 C 标准的哪个部分或哪个编码指南来证明答案的合理性?
【问题讨论】:
不,特别是对于inline,这些不应该相同。
但是这个例子从一开始就是错误的。对于inline,您需要在.h 文件中使用inline 进行定义(整个函数)。通过 inline,您可以避免符号在包含 .h 标头的多个翻译单元 (.c) 中定义。
然后,在一个翻译单元中,您只需将不带inline 的声明噘起,以表明该符号应在相应的.o 目标文件中生成。
【讨论】:
inline 根本没有意义。无论如何,编译器可以内联它看到的每个定义。
-O1 优化的免费版本不会自动内联小函数(但你可以用inline 哄它这样做),而带有-O2 或@ 的高级版本987654330@ 优化确实如此。但我的问题很笼统+我正在寻找涵盖clang / gcc / XC16的建议。
inline 的定义放在标题中(或 .c 的开头)并放置一个“实例化”,没有inline 的声明,稍后。这样您就可以确定它是可移植的。
我想提供有关内联的详细信息,
你可以把声明和定义分开,但是那 定义必须在使用 功能,即在您的情况下
inline static int foo(int x);
内联函数包含在 ISO C99 标准中,但目前 GCC 实现的功能与 ISO C99 标准要求的功能之间存在很大差异。
要声明内联函数,请在其声明中使用 inline 关键字,如下所示:
static inline int
inc (int *a)
{
return (*a)++;
}
请注意,函数定义中的某些用法可能使其不适合内联替换。
请注意,在 C 中,与 C++ 不同的是,inline 关键字不会影响函数的链接。
【讨论】:
是的。内联和静态应该包括在内。例如,函数的代码行在您声明的 .h 文件和您定义的 .c 文件中应该是相同的(在这两种情况下都是如此),但在您的主 code.c 文件中它应该只调用时具有函数名称,因此“foo(传递的参数)”。
希望这会有所帮助!
【讨论】:
您只需要在声明中使用inline static。您可以将其排除在函数定义之外。
7.1.1/6:
在没有存储类说明符的命名空间范围内声明的名称具有外部链接,除非它由于先前的声明而具有内部链接并且如果它没有声明为 const。声明为 const 且未显式声明为 extern 的对象具有内部链接。
【讨论】:
inline 附加到声明而不附加到定义是毫无意义的。