c++ - 我可以安全地使用#ifdef 来了解是否包含 c++ std header 吗?

标签 c++ c-preprocessor std header-files

首先,我读过这个问题:Is there a way to detect portably that a standard header is included using macros?

我想知道的是:使用 #ifdef 检测是否包含 c++ std header 的安全性如何,如下面的代码所示:

namespace overwrite
{
    using byte = unsigned char;

    template <bool safeMode = true, typename generic>
    void withZeros( generic *toBeOverwriten, size_t length = 1 )
    {
         // do stuff
    }

    #ifdef _GLIBCXX_RANDOM // found this macro inside <random>
    template <bool safeMode = true, typename generic>
    void withRandomData( generic *toBeOverwriten, byte min = 0, byte max = 255 )
    {
        // do stuff expecting <random> to be included
    }
    #endif
}

...这样我就不能像对上述问题的回答中提出的那样将某些标准函数重载为“更差的匹配”,而且还可以编译或不编译我的头文件的整个函数/部分,具体取决于包含一些标准 header 。

我怀疑这种方式一点也不安全吗?如果是这样,是否有任何其他方法可以检测到这一点以执行我想执行的操作?

关于“我为什么不只包含标题”...

我给出的示例代码只是一个示例。我脑子里还有其他事情,只是想知道是否有另一种方法可以检查是否包含 header ,而无需检查您希望在其中定义的宏。然后我想起了我问自己这个问题的真实情况,然后我开始问我在问什么......因为在这种情况下,我不想包含很多代码( <random> 长于 20或 30 LOC)只是为了“维持”我的 header 的单个功能。

最佳答案

有人建议c++17 添加__has_include 宏。

最新版本尚未公开,但在上次标准 session 上讨论(批准?):https://www.reddit.com/r/cpp/comments/3q4agc/c17_progress_update_oct_2015/

上一个版本:http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/p0061r0.html


在那之前,我不认为有一种可移植的方法来检测 header 是否可用。你能做的最好的事情就是检查头文件定义了什么宏,记住不同的库有不同的宏,即使在同一个库中,名称也会随着修订版本的不同而改变,因为它是一个内部宏。如果您只想支持主要的编译器(有 3 个)并且不希望您的代码在 3-5 年后得到支持,这并没有那么糟糕。

如果可能的话,您应该检查功能,而不是检查标题。 C++11 之后定义了一组功能测试宏:

http://en.cppreference.com/w/User:D41D8CD98F/feature_testing_macros

关于c++ - 我可以安全地使用#ifdef 来了解是否包含 c++ std header 吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33455164/

相关文章:

c++ - 在带有 union 的类中使用 'memcpy()'

c++ - vim、ctags 和同名标识符

c - 通过 C 预处理器定义偏移量的最佳方法

c - 计算存储数字 n 所需位数的宏

c++ - 与 unordered_map vector 一起使用的 scoped_allocator_adaptor 的最小示例中的段错误

c++ - 为什么我得到字符串没有命名类型错误?

c++ - 在 std 命名空间 : any guarantees? 中定义的友好类

c++ - A() = A() - 为什么编译?

c++ - 我想捕获一个异常并将其捆绑在我自己的异常中并向上抛出

c++ - 在 C 和 C++ 中解析 typedef