我使用clang ++ - 600.0.51编译以下代码:
template<typename ... Args> struct seq{};
template<typename Seq, size_t c = 1> struct pop_back;
template<typename ... Args> struct pop_back <seq<Args...>, 0>{
typedef seq<Args...> type;
};
template<typename ... Args, typename T, size_t c> struct pop_back <seq<Args..., T>, c>{
typedef typename pop_back<seq<Args...>, c - 1>::type type;
};
我得到一个错误:类模板部分特化包含模板参数 无法推断;永远不会使用这种局部特化[-Werror]
似乎我以错误的方式专注于可变参数模板,但是gcc 4.8.2和vc 2013可以成功编译它。如果我只是如上所述定义pop_back,那么gcc和vc都会被传递。如果我实例化pop_back,它们都会失败。
我的代码不标准吗?如何为此编写解决方法?
答案 0 :(得分:3)
T
,因为编译器无法确定参数包Args...
的结尾。你需要一个不同的实现。当c
减少时,这个连接序列的各个元素。
namespace detail
{
template <typename S1, typename S2>
struct concat_impl;
template <typename... Ts, typename... Us>
struct concat_impl<seq<Ts...>, seq<Us...>>
{
using type = seq<Ts..., Us...>;
};
template <typename S1, typename S2>
using concat = typename concat_impl<S1, S2>::type;
template <typename Seq, size_t c = 1, typename = void>
struct pop_back;
template <typename T, typename... Args, size_t c>
struct pop_back<seq<T, Args...>, c, typename std::enable_if<c!=0>::type>
{
using type = concat<seq<T>, typename pop_back<seq<Args...>, c-1>::type>;
};
template <typename... Args>
struct pop_back<seq<Args...>, 0>
{
using type = seq<>;
};
} // detail
template <typename Sequence, size_t c>
struct pop_back;
template <typename... Args, size_t c>
struct pop_back<seq<Args...>, c> : detail::pop_back<seq<Args...>, sizeof...(Args) - c>
{ };