使用 IFDEF 和 IFNDEF 指令包含头文件

using ifdef and ifndef directives to include header files

提问人:SSR 提问时间:12/17/2021 更新时间:12/17/2021 访问量:1884

问:

请原谅我的基本问题和糟糕的编程知识。

我有一个实现,我需要在我的许多项目中使用。但是,对于不同的项目,包含的头文件是不同的。

假设我有要在 projecta.c 和 projectb.c 中使用的 spi.h 头文件。但是projectb.c中不需要特定的include(definitions.h),那么我如何使它包含特定于项目?

我已经看到这是通过 #ifdef、#ifndef 和指令来完成的。但是有人可以帮我了解它是如何完成的。

谢谢

C++ C 包括 预处理器指令 using 指令

评论

0赞 Pepijn Kramer 12/17/2021
您可能也可以只使用一次 #pragma。要使包含文件特定于项目:将它们放在源文件夹中,对于“共享”头文件,将它们放在共享文件夹中,对于 sdk 头文件,将它们放在 sdk 文件夹中。
2赞 Bodo 12/17/2021
请不要描述你的代码,而是展示一个例子。目前尚不清楚究竟将包括在哪里?在 或 ?在?请编辑您的问题并显示一个最小的可重复示例definitions.hprojecta.cprojectb.cspi.h

答:

0赞 Ingo Leonhardt 12/17/2021 #1

您可以根据类似情况包含某个标头:#ifdef

#ifdef INCL_DEFINITIONS
#   include "definitions.h"
#endif

在您需要的项目中,您必须添加到编译器参数中definitions.h-DINCL_DEFINITONS

评论

0赞 SSR 12/17/2021
在此之前,我们必须定义INCL_DEFINITIONS:比如,#define INCL_DEFINITIONS
0赞 Ingo Leonhardt 12/17/2021
那是完成的 bei “-DINCL_DEFINITONS”
2赞 eerorika 12/17/2021 #2

假设我有要在 projecta.c 和 projectb.c 中使用的 spi.h 头文件。但是projectb.c中不需要特定的include(definitions.h),那么我如何使它包含特定于项目?

喜欢这个:

// projecta.c
#include "spi.h"
#include "definitions.h"

// projectb.c
#include "spi.h"

不需要指令。ifdef

0赞 Eric Postpischil 12/17/2021 #3

我已经看到这是通过 #ifdef、#ifndef 和指令来完成的。

它可以通过 和 指令或指令来完成。#ifdef#ifndef#if

其中的关键部分是,您需要某种方法来根据正在构建的项目来定义预处理器宏。一种常见的方法是:

  • 每个项目都有自己的生成设置。
  • 这些生成设置包括传递给编译器的选项。
  • 编译器具有用于定义预处理器符号的选项。

例如,对于 GCC 和 Clang,您可以使用 to 导致定义(没有替换标记;它已定义,但定义为空)或 -Dsymbol=replacement 来使它使用指示的 .-Dsymbolsymbolreplacement

一旦你有了这个,就可以选择如何使用它。一种选择是,如果应包含要素,则定义符号,如果不包含,则不定义符号。然后,您将拥有如下指令:

#if defined FeatureX
    #include "HeaderForFeatureX.h"
#endif

另一种选择是将符号定义为 1(如果应包含要素)和 0(如果不包括)。那么你会得到:

#if FeatureX
        #include "HeaderForFeatureX.h"
#endif

从历史上看,有些人使用第一种选择,有些人使用第二种选择。因此,编写设置和代码来涵盖两者是很常见的。当使用编译器选项定义一个符号时,我们将定义它(满足第一种方法)并将其定义为 1(满足第二个方法),就像 一样。在测试它时,我们将使用 with 进行测试,因为如果使用任一选项,则为 true,而仅当定义为 1 时才为 true,而不仅仅是使用空替换标记定义。-DFeatureX=1#if defined FeatureX#if FeatureXFeatureX

(在指令中,如果可以作为预处理器宏名称的标记不是定义的预处理器宏名称,则将其替换为 。因此,如果未定义,则变为 。#if0FeatureX#if FeatureX#if 0

第三种选择是根据所选特征定义具有不同值的符号。例如,我们可以定义为 10、20 或 30,然后使用如下指令:ProductLevel

#if 10 <= ProductLevel
    #include "Level10Features.h"
    #if 20 <= ProductLevel
        #include "Level20Features.h"
        #if 30 <= ProductLevel
            #include "Level30Features.h"
        #endif
    #endif
#endif