2017-02-18 61 views
2

考虑布尔特技以检查是否一堆类型都是相同的类型:布尔特技和模板的模板参数

template<typename Type, typename... Types> 
static constexpr bool allOf = std::is_same< 
    std::integer_sequence<bool, true, std::is_same<Type, Types>::value...>, 
    std::integer_sequence<bool, std::is_same<Type, Types>::value..., true> 
>::value; 

作为一个例子,可以使用它,因为它遵循以检查是否所有的参数是int值:

template<typename... Args> 
void f(Args&&... args) { 
    static_assert(allOf<int, Args...>, "!"); 
    // ... 
} 

有没有什么办法与给定模板的模板参数的特用呢?
作为一个例子,用下面的代码:

template<typename> struct S {}; 

template<typename... Args> 
void f(Args&&... args) { 
    static_assert(allOf<S, Args...>, "!"); 
    // ... 
} 

allOf变量应被定义为:

template<template<typename> class Type, typename... Types> 
static constexpr bool allOf = ???; 

我想检查在Types每个T是如下形式的专门S<U>,不管什么是U

可能吗?

+2

将bool招很好,谁提出了这个? –

+0

@ JohannesSchaub-litb我不记得我在哪里找到它了,反正它在这里。我遇到的版本是使用结构建立的,“std :: conditional”,“std :: true_type”和“std:.false_type”。当我发现变量模板比原始模板更紧凑时,我开始使用这个模板。 – skypjack

+0

不错的把戏,无论如何 – max66

回答

1

怎么样如下?

template <typename> 
struct S 
{ }; 

template <template <typename> class, typename> 
struct isS 
{ static constexpr bool value { false } ; }; 

template <template <typename> class S, typename U> 
struct isS<S, S<U>> 
{ static constexpr bool value { true } ; }; 

template<template<typename> class Type, typename... Types> 
static constexpr bool allOf = std::is_same< 
    std::integer_sequence<bool, true, isS<Type, Types>::value...>, 
    std::integer_sequence<bool, isS<Type, Types>::value..., true> 
>::value; 
+0

它看起来很长好。我不知道为什么它没有出现在我的脑海里。我不应该在夜间制造问题,而是在紧接着的那个早上再次思考问题。 :-D +1因为这是一个可行的解决方案,让我们看看在接受之前是否还有其他的东西出现。 – skypjack

+1

@skypjack - 它只是因为午夜才出现在你的脑海里;并在午夜时分,我在我最好的:-) – max66

+0

有一个可能的解释:你没有​​儿子。你做? :-D – skypjack

5

我们只需要一个专门的检查:

template <class T, template <class...> class Z> 
struct isZ : std::false_type { }; 

template <class... Args, template <class...> class Z> 
struct isZ<Z<Args...>, Z> : std::true_type { }; 

和更通用实现的allOf

template <bool... bs> 
using allOf = std::is_same< 
    std::integer_sequence<bool, true, bs...>, 
    std::integer_sequence<bool, bs..., true>>; 

随着指出:

static_assert(allOf<isZ<decay_t<Args>, S>::value...>::value, "!");