【问题标题】:Does using `__DATE__` or `__TIME__` violate the one-definition-rule?使用 `__DATE__` 或 `__TIME__` 是否违反单一定义规则?
【发布时间】:2016-12-21 08:18:00
【问题描述】:

在头文件中使用__DATE____TIME__ 时,包含该头文件的预处理器的结果可能会有所不同。

在什么情况下在头文件中使用__DATE____TIME__会违反单定义规则?

作为后续:assert 标头是否违反单一定义规则?

【问题讨论】:

    标签: c++ datetime c-preprocessor one-definition-rule


    【解决方案1】:

    如果__TIME__ 为不同的翻译单元提供不同的结果,则不得在需要跨翻译单元获得相同结果的上下文中使用它。这意味着例如将对象(例如类成员)初始化为 __TIME__,其中该初始化程序是包含在多个翻译单元中的标头的一部分,将会有问题。

    __DATE__ 如果您开始新构建,则不太可能为不同的翻译单元提供不同的结果,但增量构建(仅重新编译已更改的文件)确实也可能成为问题。

    assert 是一个宏,其扩展方式取决于 NDEBUG 在包含其标头时的定义方式,因此整个项目必须就是否应定义 NDEBUG 达成一致,或者标头中定义的函数应避免使用assert.

    【讨论】:

      【解决方案2】:

      单一定义规则仅适用于变量、函数、类类型、枚举或模板(例如,第 3.2 节、ISO/IEC 14882、1998 C++ 标准)。 __DATE____TIME__ 都是扩展为字符串文字的预定义宏 - 这不是单一定义规则适用的事物之一。

      assert() 也是一个预处理器宏。如果它的扩展定义了一个变量、函数、类类型、枚举或模板,那么如果该定义在翻译单元之间不同,那么它的使用可能会违反单一定义规则。从实用的角度来看,很难想象一个实现会有一个扩展为这样一个定义的assert() 宏。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-12-08
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多