【问题标题】:Should standards be specified in source code or in CPPFLAGS?标准应该在源代码中还是在 CPPFLAGS 中指定?
【发布时间】:2011-06-08 12:47:02
【问题描述】:

#define _BSD_SOURCE 还是设置 CPPFLAGS=-D_BSD_SOURCE 更好?

在我看来,如果一段源代码依赖于特定的标准,最好在代码本身中用#define 明确说明它。但是,很多评论建议在编译行指定标准更合适。从源代码中省略标准,只在编译时指定有什么好处?

【问题讨论】:

    标签: c++ c build-process compilation


    【解决方案1】:

    如果您在源代码中指定定义,则存在相同的头文件可能包含在多个源文件(翻译单元)中但具有不同预处理器定义的风险,这可能导致违反一个定义规则,这通常是一种痛苦调试。

    通过为整个项目而不是在单个源文件中指定定义,可以最大限度地减少违反单一定义规则的可能性。

    此外,如果需要添加新定义,您只需更改一个 makefile,而不是所有源文件。

    【讨论】:

    • 但是您可以为每个翻译单元使用不同的标准。如果除了一个 TU 使用 gnu 扩展外,整个项目都符合 C89,那么 #define _GNU_SOURCE 是否比污染整个项目更好?这样,如果我在其他一些 TU 中使用依赖于比 C89 更现代标准的函数,但我不知道这种依赖,我会在编译时知道它。如果整个项目都依赖于现代标准,那么移除依赖就更加困难了。
    • 我必须承认,我从来没有在一个二进制文件中混合和匹配需要不同标准(或预处理器定义)的源。如果我这样做了,我仍然会在 makefile 中指定该特定源的标志(作为目标特定变量),因为我所有的编译器标志都在 makefile 中的一个位置。此外,我经常在不同平台上使用不同的编译器(g++、SunCC)编译我的源代码,因此平台特定的 makefile 是容纳特定平台定义的正确位置。
    • @William:问题在于,如果您尝试在不同的翻译单元中混合使用不同的标准,则无法保证您可以安全地将生成的对象链接到单个可执行文件中。它可能有效,也可能失败,或者看似有效,但在运行时会为您提供微妙、难以诊断的问题。
    • 您还可以为那些需要在您的 makefile 中进行不同定义的翻译单元使用特定目标。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-07-24
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多