有没有一个编译器错误暴露我的实现is_complete类型trait? [英] Is there a compiler bug exposed by my implementation of an is_complete type trait?

查看:162
本文介绍了有没有一个编译器错误暴露我的实现is_complete类型trait?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我写了这个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
<< '\\\
';
}



我希望测试程序打印 10 ,这是我使用clang 3.4编译时得到的输出。然而,当使用gcc 4.9编译时,它打印 11 而不是 - 错误地识别类未完成为完成。 >

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



问题1:我的代码是否正确?

问题2:我在其中一个编译器中发现错误吗?



编辑:



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

解决方案

问题似乎是 void_t 的定义。定义为

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

template< typename ... ts>
using void_t = typename make_void< Ts ...> :: type;改为产生正确的结果( 10



两个编译器(演示)。



我相信这是与 N3911 ,提出 void_t CWG问题1558 。本质上,标准不清楚别名模板特化中未使用的参数是否可能导致替换失败或简单地忽略。委员会2014年11月会议通过的CWG问题的决议澄清了问题中 void_t 的较短定义应该有效,GCC 5.0执行该决议。 p>

I wrote this C++11 trait template to check whether a type is complete:

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
{};

and tested it like this:

struct Complete {};

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

I expected the test program to print 10, and that is the output I get when I compile it with clang 3.4. However, when compiled with gcc 4.9, it prints 11 instead -- mistakenly identifying class Incomplete as complete.

I don't know for sure if my code is correct, but it seems to me that even if it's wrong, it should behave the same on both compilers.

Question 1: Is my code correct?
Question 2: Have I found a bug in one of the compilers?

EDIT:

I'm not asking for a replacement for my code. I'm asking whether there is a bug in gcc or clang, and whether or not this particular construct is correct.

解决方案

The problem appears to be with the definition of void_t. Defining it as

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

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

instead yields the correct result (10) on both compilers (Demo).

I believe this is the same issue noted in section 2.3 of N3911, the paper proposing void_t, and CWG issue 1558. Essentially, the standard was unclear whether unused arguments in alias template specializations could result in substitution failure or are simply ignored. The resolution of the CWG issue, adopted at the Committee's November 2014 meeting, clarifies that the shorter definition of void_t in the question should work, and GCC 5.0 implements the resolution.

这篇关于有没有一个编译器错误暴露我的实现is_complete类型trait?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆