Jix*_*xxy 3 c++ enums templates
假设我有一个类Class,它有一个关联的枚举成员Enum。枚举仅在此类的上下文中才有意义,因此它是在其中指定的。Class::Enum::Something然后你就可以从课堂外打电话,这很好。
class Class
{
public:
enum class Enum : uchar
{
Something
}
}
Run Code Online (Sandbox Code Playgroud)
但是,如果类Class是模板化的,则不能执行Class::Enum::Something,但必须执行Class<T>::Enum::Something(或者Class<>::Enum::Something如果T有某种默认类型)。
template <typename T = double>
class Class
{
public:
enum class Enum : uchar
{
Something
}
}
Run Code Online (Sandbox Code Playgroud)
所有 s 都必须Enum相同T,因为它只是一个简单的枚举,但T无论如何都必须指定always。
我的问题是 - 有没有一种聪明的方法来避免这种情况?
必须了解的是,对于不同的专业化,包装的枚举类型是不同的Class类型。
#include <type_traits>
template <typename T = double>
struct S
{
enum class E : int { a };
};
static_assert(!std::is_same_v<S<>::E, S<int>::E>); // !!!
Run Code Online (Sandbox Code Playgroud)
看起来您希望它实际上是相同的类型,在这种情况下,您可以将其分解为一个单独的类,并使用私有实现继承通过类模板专业化来公开它:
#include <type_traits>
namespace detail {
struct Base {
enum class E : int { a };
};
} // namespace detail;
template <typename T = double>
struct S : private detail::Base
{
using Base::E;
};
static_assert(std::is_same_v<S<>::E, S<int>::E>); // OK
Run Code Online (Sandbox Code Playgroud)
但是,如果您打算提供此枚举作为各种类模板专业化的成员(上面的别名声明),则您将需要限定您引用的专业化。
S<>::E;
S<int>::E;
Run Code Online (Sandbox Code Playgroud)
您似乎想要解决的根本问题是范围界定,在这种情况下,您可以使用名称空间而不是类来包装关联的枚举:
namespace my_lib {
template <typename T = double>
struct S {};
enum class E : int { a };
} // namespace my_lib
Run Code Online (Sandbox Code Playgroud)