函数签名中未展开的参数包。

4
新版GCC引入了新的内建函数__integer_pack来帮助实现std::make_integer_sequence等函数。由于某些原因,我无法使用此函数,因此我正在尝试重新实现它(然后使用#define替换标准库用法)。
它的形式为__integer_pack(N)...,其中展开了其“返回值”。但是,我无法使我的模板类型与之匹配,在clang(10)中出现错误:
error: pack expansion does not contain any unexpanded parameter packs

using make_integer_sequence = integer_sequence<_Tp, integer_pack(_Num)...>;

这是可行的吗?

以下是我的进展:

#include <cstddef>


template <std::size_t...> struct index_sequence {};

template <std::size_t N, std::size_t... Is>
struct integer_pack : integer_pack<N - 1, N - 1, Is...> {};

template <std::size_t... Is>
struct integer_pack<0u, Is...> : index_sequence<Is...> { using type = index_sequence<Is...>; };


// Assume nothing below here can be changed.
#include <iostream>

/// Class template integer_sequence
template<typename _Tp, _Tp... _Idx>
struct integer_sequence
{
    typedef _Tp value_type;
    static constexpr size_t size() noexcept { return sizeof...(_Idx); }
};

// debugging aid
template<typename T, T... ints>
void print_sequence(integer_sequence<T, ints...> int_seq)
{
    std::cout << "The sequence of size " << int_seq.size() << ": ";
    ((std::cout << ints << ' '),...);
    std::cout << '\n';
}

template<typename _Tp, _Tp _Num>
using make_integer_sequence = integer_sequence<_Tp, integer_pack(_Num)...>;

int main()
{
    print_sequence(make_integer_sequence<int, 20>{});
}

正如所说,您尝试扩展模板的实例化而不是包。普通的 C++ 包不是这样工作的,您需要额外的步骤。 - bipll
1
__integer_pack是一种内置函数,允许对std::make_integer_sequence进行独特的实例化,而不是使用O(n)O(log(n))。您无法复制该内置函数,必须以另一种方式重新实现std::make_integer_sequence - Jarod42
你为什么认为 integer_pack(_Num)... 应该有效? - user253751
2
也许C++14实现make_integer_sequence可以帮助你? - Ted Lyngmo
1
@user253751 因为 __integer_pack(_Num)... 是在 utility STL 头文件中使用的。 - LordAro
@LordAro __integer_pack 的定义方式和 integer_pack 一样吗? - user253751
1个回答

4
不,这是不可能的。__integer_pack不是一个函数,而是编译器扩展为参数包的占位符。这是您无法在语言中复制的内容。
您可以查看gcc如何实现将对__integer_pack的调用替换为其在gcc/cp/pt.c中的扩展,从3750行开始。builtin_pack_fn_p()标识对__integer_pack的调用(_p后缀表示“谓词”),而expand_integer_pack执行扩展。
您需要在语言中编写自己的实现(或复制现有实现)。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接