小工具知识网

当前位置: 首页 > 行业知识 > C/C++条件编译:#ifdef、#else、#endif等

行业知识

C/C++条件编译:#ifdef、#else、#endif等

2026-11-05 09:02:52 来源:互联网转载

文章目录

  • #undef指令
  • 从C预处理器角度看已定义
  • 条件编译
    • 1.#ifdef、#else和#endif指令
    • #ifndef指令
      • #ifndef指令通常用于防止多次包含一个文件
      • 程序使用#ifndef避免文件被重复包含
      • #if和#elif指令
        • 条件编译还有一个用途是让程序更容易移植
        • 参考

          程序员可能要为不同的工作环境准备C程序和C库包。不同的环境可能

          使用不同的代码类型。预处理器提供一些指令,程序员通过修改#define的值

          即可生成可移植的代码。#undef指令取消之前的#define定义。#if、#ifdef、

          #ifndef、#else、#elif和#endif指令用于指定什么情况下编写哪些代码。#line

          指令用于重置行和文件信息,#error指令用于给出错误消息,#pragma指令用

          于向编译器发出指令。

          #undef指令

          #undef指令用于“取消”已定义的#define指令。也就是说,假设有如下定义:

          #define LIMIT 400

          然后,下面的指令:

          #undef LIMIT

          将移除上面的定义。现在就可以把LIMIT重新定义为一个新值。即使原

          来没有定义LIMIT,取消LIMIT的定义仍然有效。如果想使用一个名称,又

          不确定之前是否已经用过,为安全起见,可以用#undef 指令取消该名字的定

          义。

          从C预处理器角度看已定义

          处理器在识别标识符时,遵循与C相同的规则:标识符可以由大写字

          母、小写字母、数字和下划线字符组成,且首字符不能是数字。当预处理器

          在预处理器指令中发现一个标识符时,它会把该标识符当作已定义的或未定

          义的。这里的已定义表示由预处理器定义。如果标识符是同一个文件中由前

          面的#define指令创建的宏名,而且没有用#undef 指令关闭,那么该标识符是

          已定义的。如果标识符不是宏,假设是一个文件作用域的C变量,那么该标

          识符对预处理器而言就是未定义的。

          已定义宏可以是对象宏,包括空宏或类函数宏:

          #define LIMIT 1000 // LIMIT是已定义的#define GOOD // GOOD 是已定义的#define A(X) ((-(X))*(X)) // A 是已定义的int q; // q 不是宏,因此是未定义的#undef GOOD // GOOD 取消定义,是未定义的

          注意,#define宏的作用域从它在文件中的声明处开始,直到用#undef指

          令取消宏为止,或延伸至文件尾(以二者中先满足的条件作为宏作用域的结

          束)。

          另外还要注意,如果宏通过头文件引入,那么#define在文件中的位置

          取决于#include指令的位置。

          稍后将介绍几个预定义宏,如__DATE__和__FILE__。这些宏一定是已

          定义的,而且不能取消定义。

          条件编译

          可以使用其他指令创建条件编译(conditinal compilation)。也就是说,

          可以使用这些指令告诉编译器根据编译时的条件执行或忽略信息(或代码)

          块。

          1.#ifdef、#else和#endif指令

          我们用一个简短的示例来演示条件编译的情况。考虑下面的代码:

          #ifdef MAVIS#include "horse.h"// 如果已经用#define定义了 MAVIS,则执行下面的指令#define STABLES 5#else#include "cow.h" //如果没有用#define定义 MAVIS,则执行下面的指令#define STABLES 15#endif

          这里使用的较新的编译器和 ANSI 标准支持的缩进格式。如果使用旧的

          编译器,必须左对齐所有的指令或至少左对齐#号,如下所示:

          #ifdef MAVIS#include "horse.h" // 如果已经用#define定义了 MAVIS,则执行下面的指令#define STABLES 5#else#include "cow.h" //如果没有用#define定义 MAVIS,则执行下面的指令#define STABLES 15#endif

          #ifdef指令说明,如果预处理器已定义了后面的标识符(MAVIS),则

          执行#else或#endif指令之前的所有指令并编译所有C代码(先出现哪个指令

          就执行到哪里)。如果预处理器未定义MAVIS,且有 #else指令,则执行

          #else和#endif指令之间的所有代码。

          #ifdef #else很像C的if else。两者的主要区别是,预处理器不识别用于标

          记块的花括号({}),因此它使用#else(如果需要)和#endif(必须存在)

          来标记指令块。这些指令结构可以嵌套。也可以用这些指令标记C语句块

          ifdef.c程序

          /* ifdef.c -- 使用条件编译 */#include #define JUST_CHECKING#define LIMIT 4int main(void){int i;int total = 0;for (i = 1; i total += 2 * i*i + 1;#ifdef JUST_CHECKINGprintf("i=%d, running total = %d\n", i, total);#endif}printf("Grand total = %d\n", total);return 0;}char first[SLEN];char last[SLEN];};// 类型定义typedef struct names_st names;// 函数原型void get_names(names *);void show_names(const names *);char * s_gets(char * st, int n);#endifnames winner = { "Less", "Ismoor" };printf("The winner is %s %s.\n", winner.first,winner.last);return 0;}

上一篇:mc正版怎么做服务器?

下一篇:数据结构:5