c++ - 查找参数包的唯一值的数量

标签 c++ c++11 template-meta-programming

给定一个带有可变参数的参数包,如何找到包中唯一值的数量。我正在寻找类似

的东西
no_of_uniques<0,1,2,1,2,2>::value // should return 3

我的基本实现看起来是这样的

template <size_t ... all>
struct no_of_uniques;
// this specialisation exceeds -ftemplate-depth as it has no terminating condition
template <size_t one, size_t ... all>
struct no_of_uniques<one,all...> {
    static const size_t value = no_of_uniques<one,all...>::value;
};
template <size_t one, size_t two, size_t three>
struct no_of_uniques<one,two,three> {
    static const size_t value = (one==two && one==three && two==three) ? 1:
                                (one!=two && two==three) ? 2:
                                (one==two && one!=three) ? 2:
                                (one==three && two!=three) ? 2: 3;
};
template <size_t one, size_t two>
struct no_of_uniques<one,two> {
    static const size_t value = one==two ? 1: 2;
};
template <size_t one>
struct no_of_uniques<one> {
    static const size_t value = 1;
};

在这里,我专门处理了最多三个参数,但可以理解的是,代码会随着参数的数量呈指数级增长。我想有一个 meta 解决方案,只使用 STL 而没有像 Boost.MPL 这样的第三方库。

可以在此处找到一个类似的问题,尽管是在检查唯一类型的上下文中,而不是查找参数包的唯一值的数量:

Check variadic templates parameters for uniqueness

在查找参数包的唯一值数量的过程中,我们可能需要先对包进行排序,并且在这个其他问题中提供了一个很好的实现

Quick sort at compilation time using C++11 variadic templates

最佳答案

这是一个简单的 O(n^2) 方法来做到这一点

template <size_t...>
struct is_unique : std::integral_constant<bool, true> {};

template <size_t T, size_t U, size_t... VV>
struct is_unique<T, U, VV...> : std::integral_constant<bool, T != U && is_unique<T, VV...>::value> {};

template <size_t...>
struct no_unique : std::integral_constant<size_t, 0> {};

template <size_t T, size_t... UU>
struct no_unique<T, UU...> : std::integral_constant<size_t, is_unique<T, UU...>::value + no_unique<UU...>::value> {};

所以使用你的例子:

no_unique<0, 1, 2, 1, 2, 2>::value; // gives 3

关于c++ - 查找参数包的唯一值的数量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37150354/

相关文章:

c++ - 在cpp中运行shellcode

c++ - unique_ptr 和指定解构函数

c++ - 递归的可变参数模板函数

c++ - g++ 编译器选项,用于警告类型转换与 ublas::bounded_vector

c++ - 使用 Weverything 和 C++11 时出现与 clang 冲突的警告

c++ - std::shared_timed_mutex 上的共享锁可以升级为独占锁吗?

c++ - 为什么非专业模板胜过部分专业模板?

c++ - 在两个不同的命名函数之间进行选择的特征有什么替代方法?

c++ - 函数局部静态 const 对象的线程安全初始化

android - 收到错误 : 'shared_ptr' in namespace 'std' does not name a type