static inline
,extern inline
和普通的inline
函数有什么区别?
我看到过一些含糊不清的解释。据我所了解,static inline
并不仅仅是指一个只能在某个文件中被引用的inline
函数,就像static
关键字通常表示的那样。我猜extern inline
也是同样的情况,它与extern
变量的解释不同。如果有任何答案,将不胜感激!
static inline
,extern inline
和普通的inline
函数有什么区别?
我看到过一些含糊不清的解释。据我所了解,static inline
并不仅仅是指一个只能在某个文件中被引用的inline
函数,就像static
关键字通常表示的那样。我猜extern inline
也是同样的情况,它与extern
变量的解释不同。如果有任何答案,将不胜感激!
static inline
定义函数会定义一个带有内部链接的内联函数。这种函数能够按照所期望的方式工作,具有这两个修饰符的通常特性: static
赋予其内部链接性,inline
则使其成为内联函数。因此,该函数是“局部”的于某个翻译单元并在其中进行内联。inline
的函数定义会定义一个带有外部链接的内联函数。但是,这样的定义被称为 内联定义,它不起到这个函数的 外部定义 的作用。这意味着即使这个函数有外部链接,除非你在其他翻译单元中提供一个单独的 外部定义 ,否则它将被视为是 未定义的。extern inline
的函数定义会定义一个具有外部链接的内联函数,同时该定义也作为该函数的 外部定义。这种函数可以从其他翻译单元中调用。extern inline
定义,或为其提供两个单独的定义:一个是 inline
,另一个是 extern
。在后一种情况下,当您调用函数时,编译器可以选择两个定义中的任意一个。extern inline void f();
看起来像是一个声明,但实际上它将之前的 inline void f() { ..... }
转换为该单元的外部定义,而不是内联定义。(参考 C11 6.7.4/7)。 - M.Minline int il_fun0(void) { return 0; } extern int il_fun0(void) { return 0; }
同时提供两个不同的定义会导致"error: redefinition of 'il_fun0'"错误(无论是否使用extern
)。因此,请提供两个单独的定义。 - chux - Reinstate Monicainline
关键字只是编译器的提示,因此无法保证您的函数调用是否会被编译为内联或普通调用。因此,我们应该为同一个内联函数准备两个定义。每个调用内联函数的翻译单元必须有自己的内联定义来处理内联。此外,只有一个翻译单元必须具有外部定义来处理正常调用。 - rosshjbinline void func(void) {}
以进行内联,并在源文件(单独的翻译单元)中放置 extern inline void func(void);
以进行普通调用。 - rosshjb