Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/141.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 断言该类型是无符号整数或具有最大大小的枚举类型_C++_C++11_Templates - Fatal编程技术网

C++ 断言该类型是无符号整数或具有最大大小的枚举类型

C++ 断言该类型是无符号整数或具有最大大小的枚举类型,c++,c++11,templates,C++,C++11,Templates,我尝试编写以下代码,以静态断言变量类型是大小小于或等于四个字节的无符号整数 我从以下几点开始: template<typename T> using is_uint_le32_t = std::integral_constant< bool, std::is_integral<T>::value && std::is_unsigned<T>::value && sizeof(T) <= sizeof(

我尝试编写以下代码,以静态断言变量类型是大小小于或等于四个字节的无符号整数

我从以下几点开始:

template<typename T>
using is_uint_le32_t = std::integral_constant<
  bool,
  std::is_integral<T>::value
  && std::is_unsigned<T>::value
  && sizeof(T) <= sizeof(uint32_t)>;
模板
使用is_uint_le32_t=std::integral_常量<
布尔,
std::is_integral::value
&&std::is_unsigned::value
&&sizeof(T);
这样我就可以编写
静态断言(is\u uint\u le32\u t)


但是,当
T
是一个枚举类型,其基础类型满足
并且我不知道如何做时,我希望这个别名模板也可以求值为
true

我们可以使用
std::conditional
获取枚举类型的基础类型,或者不使用任何其他类型:

#include <type_traits>

namespace std_compat {
#if __cplusplus >= 202002L
    using ::std::type_identity;
#else
    template <typename T>
    struct type_identity {
        using type = T;
    };
#endif
}

template <typename T>
using underlying_or_id_t = typename std::conditional<
    std::is_enum<T>::value, std::underlying_type<T>, std_compat::type_identity<T>
    >::type::type;

template<typename T>
using is_uint_le32_no_enum = std::integral_constant<
    bool,
    std::is_integral<T>::value
    && std::is_unsigned<T>::value
    && sizeof(T) <= sizeof(uint32_t)>;

template<typename T>
using is_uint_le32_t = is_uint_le32_no_enum<underlying_or_id_t<T>>;
#包括
名称空间std_compat{
#如果uu cplusplus>=202002L
使用::std::type_标识;
#否则
模板
结构类型标识{
使用类型=T;
};
#恩迪夫
}
模板
使用基础\u或\u id\u t=typename std::conditional<
std::is_enum::value,std::底层_类型,std_compat::type_标识
>::类型::类型;
模板
使用is_uint_le32_no_enum=std::integral_常量<
布尔,
std::is_integral::value
&&std::is_unsigned::value
&&sizeof(T);
模板
使用is_uint_le32_t=is_uint_le32_no_enum;

我们可以使用
std::conditional
获取枚举类型的基础类型,或者不使用任何其他类型:

#include <type_traits>

namespace std_compat {
#if __cplusplus >= 202002L
    using ::std::type_identity;
#else
    template <typename T>
    struct type_identity {
        using type = T;
    };
#endif
}

template <typename T>
using underlying_or_id_t = typename std::conditional<
    std::is_enum<T>::value, std::underlying_type<T>, std_compat::type_identity<T>
    >::type::type;

template<typename T>
using is_uint_le32_no_enum = std::integral_constant<
    bool,
    std::is_integral<T>::value
    && std::is_unsigned<T>::value
    && sizeof(T) <= sizeof(uint32_t)>;

template<typename T>
using is_uint_le32_t = is_uint_le32_no_enum<underlying_or_id_t<T>>;
#包括
名称空间std_compat{
#如果uu cplusplus>=202002L
使用::std::type_标识;
#否则
模板
结构类型标识{
使用类型=T;
};
#恩迪夫
}
模板
使用基础\u或\u id\u t=typename std::conditional<
std::is_enum::value,std::底层_类型,std_compat::type_标识
>::类型::类型;
模板
使用is_uint_le32_no_enum=std::integral_常量<
布尔,
std::is_integral::value
&&std::is_unsigned::value
&&sizeof(T);
模板
使用is_uint_le32_t=is_uint_le32_no_enum;

对于任何关心此事的人,我刚刚提出了一个可能更简单的解决方案:

template<typename T>
constexpr typename std::enable_if<std::is_integral<T>::value, bool>::type
is_uint_le32_t()
{ return std::is_unsigned<T>::value && sizeof(T) <= sizeof(uint32_t); }

template<typename T>
constexpr typename std::enable_if<std::is_enum<T>::value, bool>::type
is_uint_le32_t()
{ return is_uint_le32_t<typename std::underlying_type<T>::type>(); }
模板
constexpr typename std::enable_if::type
是(u uint)le32(u t)

{return std::is_unsigned::value&&sizeof(T)对于任何关心的人,我刚刚提出了一个可能更简单的解决方案:

template<typename T>
constexpr typename std::enable_if<std::is_integral<T>::value, bool>::type
is_uint_le32_t()
{ return std::is_unsigned<T>::value && sizeof(T) <= sizeof(uint32_t); }

template<typename T>
constexpr typename std::enable_if<std::is_enum<T>::value, bool>::type
is_uint_le32_t()
{ return is_uint_le32_t<typename std::underlying_type<T>::type>(); }
模板
constexpr typename std::enable_if::type
是(u uint)le32(u t)

{return std::is_unsigned::value&&sizeof(T)制作另一个模板以测试类型或基础类型是否满足条件的明显解决方案有什么问题?您尝试了哪些不起作用的方法?制作另一个模板以测试类型或基础类型是否满足条件的明显解决方案有什么问题?您尝试过哪些不起作用的方法?在这里使用
类型一致性
而不是简单地使用
t
,有什么意义呢?@super我们不能在
条件
中包含
基础类型::类型
,因为这对于非枚举是格式错误的,
条件
无法避免该错误。因此最终的
::type
需要在
条件之外,但是在非枚举的情况下,我们需要
::键入
以“展开”某些内容以返回
T
(另外,现在我认为部分专门化解决方案会更简单…)啊,对了。我刚刚意识到你有双重
::type::type
外部
条件
用于此目的。这现在是有意义的了。@aschepler:这正是我一直在努力解决的问题,回答得很好。在这里使用
类型一致性
而不是简单地使用
T
,有什么意义呢?@super我们不能有
底层type::type
条件
内,因为这对于非枚举是格式不正确的,并且
条件
不能避免该错误。因此最后的
::type
需要在
条件
外,但是在非枚举的情况下,我们需要
::type
来“展开”要返回到
t
的内容。(还有,现在我想部分专门化解决方案会更简单…)啊,对了。我刚刚意识到你有双重
::type::type
外部
条件
。这现在是有意义的。@aschepler:这正是我一直在努力解决的问题,回答得很好。