6. 条件编译

条件编译 是在 预处理阶段 让编译器根据给定的条件来选择性的将某些代码参与编译。它在 C 语言的项目管理和代码跨平台移植 中起到了至关重要的作用。

条件编译的指令如下

指令
说明
#if 常量表达式
常量表达式为真值则参加编译。
#ifdef 宏名
如果已有宏定义则参加编译。
#ifndef 宏名
如果没有宏定义则参加编译。
#elif 常量表达式
上述三种指令的子语句,用于再次判断 常量表达式 的值来决定是否参加编译。
#else
条件编译的子语句,上述条件都不成立则参加编译。
#endif
条件编译的结束标记
defined(宏名)
用于常量表达式中,如果宏名已经定义则返回 1,否则返回 0

条件编译的语法只有三种:

语法1

#if 常量表达式1
  ...
#elif 常量表达式2
  ...
#else
  ...
#endif

语法2

#ifdef 宏名
  ...
#elif 常量表达式2
  ...
#else
  ...
#endif

语法3

#ifndef 宏名
  ...
#elif 常量表达式2
  ...
#else
  ...
#endif

说明:

  1. 条件表达式必须以 #if#ifdef#ifndef其中的一个开始。
  2. 条件表达式必须以 #endif 结束。
  3. #elif 可以有 0 个、1 个或多个,可以用于再次判断。
  4. #else 用于以上都不成立的情况参加编译。且只能放在最后。

示例1

根据宏定义 ZH_CNZH_HKZH_MOKO_KR 分别定义软件不同语言的发行版。

// filename: cond_comp.c
#include <stdio.h>

#define ZH_CN
// #define ZH_HK
// #define ZH_MO
// #define KO_KR

int main(int argc, char * argv[]) {
#ifdef ZH_CN
    printf("欢迎来到北京!\n");
#elif defined(ZH_HK) || defined(ZH_MO)
    printf("歡迎來到北京!\n");
#elif defined(KO_KR)
    printf("베이징에 어서 오세요!\n");
#else
    printf("welcome to beijing!\n");
#endif
    return 0;
}

编译和运行结果如下

weimingze@mzstudio:~$ gcc -o cond_comp cond_comp.c
weimingze@mzstudio:~$ ./cond_comp
欢迎来到北京!

修改写上述代码,给 #define ZH_CN 添加注释 ,去掉 #define ZH_HK 的注释,如下:

// filename: cond_comp.c
#include <stdio.h>

// #define ZH_CN
#define ZH_HK
// #define ZH_MO
// #define KO_KR

int main(int argc, char * argv[]) {
#ifdef ZH_CN
    printf("欢迎来到北京!\n");
#elif defined(ZH_HK) || defined(ZH_MO)
    printf("歡迎來到北京!\n");
#elif defined(KO_KR)
    printf("베이징에 어서 오세요!\n");
#else
    printf("welcome to beijing!\n");
#endif
    return 0;
}

编译和运行结果如下

weimingze@mzstudio:~$ gcc -o cond_comp cond_comp.c
weimingze@mzstudio:~$ ./cond_comp
歡迎來到北京!

可见在使用不同的宏定义时,参与编译的 printf 函数也是不同的。

实验:

  1. 尝试使用 #if 常量表达式 的方式进行条件编译,如 #if 1#if 100 > 50等方式进行条件编译。