【问题标题】:Is there a compiler bug exposed by my implementation of an is_complete type trait?我的 is_complete 类型特征的实现是否暴露了编译器错误?
【发布时间】:2014-11-08 02:42:03
【问题描述】:

我写了这个 C++11 trait 模板来检查一个类型是否完整:

template <typename...>
using void_t = void;

template <typename T, typename = void>
struct is_complete : std::false_type
{};

template <typename T>
struct is_complete<T, void_t<decltype(sizeof(T))>> : std::true_type
{};

并像这样测试它:

struct Complete {};

int main()
{
    std::cout << is_complete<Complete>::value
              << is_complete<class Incomplete>::value
              << '\n';
}

我希望测试程序打印10,这就是我用clang 3.4 编译它时得到的输出。但是,当使用 gcc 4.9 编译时,它会打印 11 —— 错误地将 class Incomplete 标识为完整。

我不确定我的代码是否正确,但在我看来,即使它是错误的,它在两个编译器上的行为也应该相同。

问题 1:我的代码是否正确?
问题 2:我是否在其中一个编译器中发现了错误?

编辑:

我不是要求替换我的代码。我在问 gcc 或 clang 中是否存在错误,以及 这个特定的构造 是否正确。

【问题讨论】:

  • @chris - 这不是重复的 - 问题是关于 gcc 或 clang 可能存在的错误。
  • 我并没有说这是一个骗局,或者投票结束。如果您想要一些适用于 GCC 和 Clang 的东西,它会很有帮助。
  • @Felics 那是我,我现在明白你的意思了。请努力使您的问题标题尽可能具有描述性。只有问题正文的最后几句话真正谈论编译器错误。远不清楚这是您提出问题的核心问题。我已为此修改了您的问题标题。很抱歉过早关闭。
  • @rubenvb 好的 - 感谢您的建议和编辑

标签: c++ templates c++11 gcc clang


【解决方案1】:

问题似乎与void_t 的定义有关。将其定义为

template<typename... Ts>
struct make_void { typedef void type;};

template<typename... Ts>
using void_t = typename make_void<Ts...>::type;

而不是在两个编译器 (Demo) 上产生正确的结果 (10)。

我相信这与N3911 的第 2.3 节中提到的问题相同,论文提出void_tCWG issue 1558。本质上,该标准不清楚别名模板特化中未使用的参数是否会导致替换失败或被忽略。在委员会 2014 年 11 月的会议上通过的 CWG 问题的决议澄清了问题中void_t 的较短定义应该有效,并且 GCC 5.0 实施了该决议。

【讨论】:

    猜你喜欢
    • 2015-10-20
    • 1970-01-01
    • 2012-10-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-12-08
    • 1970-01-01
    相关资源
    最近更新 更多