Pourquoi ce modèle variadique imbriqué est-il un argument invalide?

Si je définis un struct template Bar qui accepte un argument template:

template <template <int,bool,char> class>
struct Bar {};

je peux instancier à l'aide d'un struct modèle Zod:

template <int,bool,char> struct Zod {};
Bar<Zod> a;

je peux aussi l'instancier à l'aide d'un imbriquée struct modèle JKL:

struct GHI {
  template <int,bool,char>
  struct JKL {};
};
Bar <GHI::JKL> b;

Pourquoi je ne peux pas instancier Bar en utilisant un variadique imbriqué struct modèle <!--12?:

template <typename ...Ts>
struct ABC {
  template <Ts ...>
  struct DEF {};
};

Bar<ABC<int,bool,char>::DEF> c;

G++ 4.9.2 se plaint d'une inadéquation de type / valeur; tandis que Clang 3.4.2 l'erreur signale que l'argument template template a des paramètres de template différents de ceux du paramètre template template correspondant.

43
demandé sur user2023370 2015-05-18 01:52:16

2 réponses

donnons au paquet de paramètres de DEF un nom pour faciliter la consultation:

template <typename ...Ts>
struct ABC {
  template <Ts ... Values>
  struct DEF {};
};

Le point clé ici est que par [temp.param] / p15,Ts... Values un pack d'extension de Ts et une déclaration d'un paramètre pack Values.

Si template-parameter [...]paramètre-déclaration que déclare un paquet de paramètres (8.3.5), puis le template-parameter est un paquet de paramètres du modèle (14.5.3). Un paquet de paramètres de template qui est un paramètre-déclaration dont le type contient un ou plusieurs paquets de paramètres NON étendus est une extension de paquet.

Depuis DEF prend un paquet de paramètre non-type, il ne correspond pas à un paramètre template qui ne prend pas les packs ([temp.arg.modèle]/p3):

modèle-argument correspond à un modèle template-parameter P quand chaque modèle paramètres dans l' template-parameter-listemodèle-argument’s correspondant de la classe de modèle ou alias modèle correspond au modèle correspondant paramètre dans le modèle-paramètres-liste de P. Deux paramètres du modèle correspondent s'ils sont du même type (type, non-type, template), pour non-type template-parameter s, leurs types sont équivalents (14.5.6.1), et pour le modèle template-parameters, chacun de leur correspondant template-parameters correspond, de manière récursive. Quand P est template-parameter-liste contient un template parameter pack (14.5.3), le template parameter pack correspondra à zéro ou plus template paramètres ou paquets de paramètres de modèle dans le template-parameter-liste de A avec le même type et la même forme que le paramètre template pack en P (ignorant si ces template paramètres paramètre de modèle pack.)

Pour être sûr, Values est plutôt bizarre pour les packs - pour chaque spécialisation de ABC,Values doit contenir un nombre fixe d'arguments - mais avec les règles actuelles c'est toujours un pack, donc les règles pour les packs s'appliquent.

5
répondu T.C. 2015-05-26 21:18:05

comme Barry l'a déjà dit à propos de:

ABC<int,bool,char>::DEF<4,true,'c'> foo

Et faire un essai et a travaillé sur Coliru en ligne compilateur gcc 5.1 c++14 dans ce site Compilateur:

#include <iostream>
 template <template <int,bool,char> class>
struct Bar {};
template <int,bool,char> struct Zod {};

Bar<Zod> a;

struct GHI {
  template <int,bool,char>
  struct JKL {};
};

Bar <GHI::JKL> b;

template <template <typename... Ts> class>
struct Base {};
template<typename... Ts>
struct Floor {};
Base<Floor> c;

template <typename... Ts>
struct ABC {
  template <Ts... val>
  struct DEF {};
};
ABC<int,bool,char>::DEF<4,true,'c'> foo;

j'ai fait une recherche et j'ai trouvé cette liste de paramètres de Template.

l'extension du paquet peut apparaître dans la liste des paramètres du modèle:

 template<typename... T> struct value_holder
{
    template<T... Values> // expands to a non-type template parameter 
    struct apply { };     // list, such as <int, char, int(&)[5]>
};

où j'ai testé quelques trucs dans le compilateur run code à: http://en.cppreference.com/w/cpp/language/parameter_pack mais aussi j' trouvé ces Ellipses et les gabarits de Variadic dans visual studio 2013: https://msdn.microsoft.com/en-us/library/dn439779.aspx

3
répondu André Luís Tomaz Dionisio 2015-05-27 17:09:47