c - C中不同宏函数/内联方法的优缺点

标签 c macros inline

According to the C FAQ ,在 C 中“内联”代码基本上有 3 种实用方法:

#define MACRO(arg1, arg2) do { \
    /* declarations */ \
    stmt1;   \
    stmt2;   \
    /* ... */  \
    } while(0)    /* (no trailing ; ) */

#define FUNC(arg1, arg2) (expr1, expr2, expr3)

为了阐明这一点,表达式中使用了参数,逗号运算符返回最后一个表达式的值。

使用 inline 声明,支持 extension to gcc and in the c99 standard .

do { ... } while (0) 方法在 Linux 内核中被广泛使用,但我没有经常遇到其他两种方法。

我指的是多语句“函数”,而不是像 MAX 或 MIN 这样的单语句函数。

每种方法的优缺点是什么?为什么在不同情况下您会选择其中一种?

最佳答案

谈到宏的具体用途,即充当“函数”的宏,我会提到在内联函数中不能拥有的宏的以下优点:

惰性参数求值。例如,像这样的宏

#define SELECT(f, a, b) ((f) ? (a) : (b))

将保留三元运算符的惰性参数求值属性:仅对选定的参数求值,而另一个不求值。一个直接的内联函数类似物会提前评估两个参数,从而完成额外的不必要的工作。

访问上下文。宏可用于实现“局部函数”的某些相似之处,即可以访问封闭函数的局部变量和参数的重复代码片段。

类型独立性(和类型参数)。宏允许您编写与类型无关的“函数”(见上例)。如果您无法摆脱类型依赖,您可以将类型作为参数传递给宏。

宏的上述属性,我作为它们的优点提出,可能被滥用导致重大失败(因此也可能作为缺点提出)。但 C 中的许多语言特性都可以这么说。

关于c - C中不同宏函数/内联方法的优缺点,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1571392/

相关文章:

c - 三元运算符可用于以下用途吗?

c - VxWorks:如何确定数据是从 DDR 而不是缓存中读取的

c++ - C++ 宏中正确的字符串/字符转换

c++ - C/C++宏扩展

c++ - C++ 中的模板和宏

c++ - 导出的 C++ 类的 boost::hash_value 内联函数

c - static inline void 和 void 有什么区别?

c++ - C 和 C++ header : Define global struct inside of another struct

c - 如何用比例而不是原始数字显示文本直方图

css - 内联 CSS 来制作列