Частичная специализация шаблона с несколькими пакеты параметров шаблонов

Продолжая свое путешествие в мир вариативных шаблонов , я столкнулся с другой проблемой.

Предполагая следующий класс шаблона:

template < typename T >
struct foo 
{
    //default implementation
};

, можно частично специализируйте его для экземпляров вариативных шаблонов следующим образом:

template < template < typename ... > class T, typename ...Args >
struct foo< T< Args... > >
{
    //specialized implementation
};

С этим, foo будет соответствовать реализации по умолчанию, а foo > в специализированную реализацию.

Однако при использовании нескольких параметров шаблона все усложняется. Например, если у нас есть следующий шаблонный класс

template < typename T, typename U >
struct bar {};

, и мы хотим частично специализировать его, как мы делали для foo , мы не можем сделать

template < template < typename ... > class T, typename ...TArgs,
           template < typename ... > class U, typename ...UArgs >
struct bar< T< TArgs... >, U< UArgs... > > {};

//This would correspond to the specialized version with
//T=std::tuple,
//TArgs=int,char
//U=std::tuple,
//UArgs=float
bar< std::tuple< int, char >, std::tuple< float > > b;

В самом деле, если я прав, у нас может быть только один пакет параметров шаблона, и он должен быть помещен в конец списка параметров. Я понимаю, почему это обязательно в объявлениях шаблонов, но для определенной частичной специализации шаблона (как в примере выше) это не должно быть проблемой.

Можно ли достичь частичной специализации шаблона с помощью нескольких пакетов параметров шаблона?


Изменить : Теперь я чувствую себя глупо ... код, который я дал выше, компилируется идеально (по крайней мере, с gcc 4.5). Ошибка компиляции у меня возникла не из-за нескольких пакетов параметров, а из-за их использования в качестве параметров функций-членов. В частичной специализации панели я попытался определить функцию-член, которая принимает оба параметра TArgs и UArgs :

template < template < typename ... > class T, typename ...TArgs, 
           template < typename ... > class U, typename ...UArgs >
struct bar< T< TArgs... >, U< UArgs... > >
{
    void method( TArgs... targs, UArgs... uargs ) //compile error here
    {
    }
};

В объявлении функции-члена gcc дает мне ошибку

пакеты параметров должны быть в конце списка параметров.

Насколько я могу судить, компилятор должен иметь возможность определять правильную функцию-член для данного экземпляра шаблона, например bar , std :: tuple > должен содержать функцию-член метод void (int, char, float) . Я делаю что-то неправильно? Или я пытаюсь сделать то, что невозможно? Если да, то есть ли веская причина, по которой это невозможно?

15
задан Community 23 May 2017 в 11:51
поделиться