Partage
  • Partager sur Facebook
  • Partager sur Twitter

nombre d'arguments variables

23 mai 2019 à 11:56:17

Bonjour,

J'ai actuellement une fonctions qui prend un nombre variable d'argument en entrée.
Au seins de cette fonction, je doit appeler un autre fonction qui prends elle aussi un nombre variables d'argument en entrée.

En fait, les arguments en entrée de la deuxième fonctions doivent exactement être ceux de la première fonction. Ainsi, j'aimerais pouvoir passer successivement tout les argument de la première à la deuxième fonction, mais je ne vois pas comment faire:

void Foo1(CString nam, ...)
{  
    // du code

    Foo2(nam, ...); // les ... de Foo2 doivent être en fait les ... de Foo1

   // du code
}

Ensuite, c'est Foo2 qui s'occupe d'extraire le nombre variable d'argument avec va_list, va_start, va_arg et va_end.

-
Edité par adrien050356 23 mai 2019 à 11:56:44

  • Partager sur Facebook
  • Partager sur Twitter
23 mai 2019 à 12:18:01

salut,

Dépêche toi d'oublier cette idée tout à fait saugrenue d'utiliser les va-lists issues du C, et renseignes toi dare dare sur la programmation générique (les classes et le fonctions template) et plus particulièrement sur le concept de variadic template ;)

Après tout, tu es dans la section C++ ici!! il n'y a donc aucune raison de coder "comme si c'était du C" ;)

  • Partager sur Facebook
  • Partager sur Twitter
Ce qui se conçoit bien s'énonce clairement. Et les mots pour le dire viennent aisément.Mon nouveau livre : Coder efficacement - Bonnes pratiques et erreurs  à éviter (en C++)Avant de faire ce que tu ne pourras défaire, penses à tout ce que tu ne pourras plus faire une fois que tu l'auras fait
23 mai 2019 à 13:12:57

c'est à dire que Foo2 existe déjà est utilise déjà cette méthode. Je l'ai récupéré comme ça et je ne peux pas me permettre de tout changer. Est-ce que ce que tu propose est quand même viable sachant que j'ai la main seulement sur Foo1 ?
  • Partager sur Facebook
  • Partager sur Twitter
23 mai 2019 à 13:25:15

A priori, je dirais que oui, mais, l'idéal restera malgré tout de t'orienter vers les variadic template:

Foo1 prendrait une forme récursive  proche de

template <typename T, typename ... ARGS>
void foo(T first, ARGS ... others){
  foo(first);
  foo(others...); 
}
/* fin de la récursivité */
template <typename T>
void foo(T first){
    /* ce qui doit être fait avec first */
}

Et, bien sur, foo2 pourrait suivre le même modèle ;).  Seulement, pour pouvoir t'en dire plus (car il y aura toujours des cas spécifiques), il faudrait que j'en sache déjà plus sur ce que doivent faire foo1 et foo2 :-°:'(:waw:

  • Partager sur Facebook
  • Partager sur Twitter
Ce qui se conçoit bien s'énonce clairement. Et les mots pour le dire viennent aisément.Mon nouveau livre : Coder efficacement - Bonnes pratiques et erreurs  à éviter (en C++)Avant de faire ce que tu ne pourras défaire, penses à tout ce que tu ne pourras plus faire une fois que tu l'auras fait
23 mai 2019 à 13:41:59

koala01 a écrit:

Dépêche toi d'oublier cette idée tout à fait saugrenue d'utiliser les va-lists issues du C, [...]

Après tout, tu es dans la section C++ ici!! il n'y a donc aucune raison de coder "comme si c'était du C" ;)

Sans parler que `CString` n'est pas un POD et que donc `func(CString, ...)`, c'est un UB.

  • Partager sur Facebook
  • Partager sur Twitter
C++: Blog|FAQ C++ dvpz|FAQ fclc++|FAQ Comeau|FAQ C++lite|FAQ BS| Bons livres sur le C++| PS: Je ne réponds pas aux questions techniques par MP.
23 mai 2019 à 16:47:23

C'est plutôt

template<class... Ts>
void Foo1(CString nam, Ts /*const&*/... xs)
{
    Foo2(nam, xs...);
}

Mais c'est étrange qu'il n'y a pas une version de Foo2 qu prend une va_list en paramètre.

PS: La récursivité avec les templates varidiaques n'est généralement pas la bonne solution, c'est beaucoup de répétition de code pour rien: https://jonathanpoelen.github.io/2013/12/parcourir-les-arguments-dune-fonction-variadique/

-
Edité par jo_link_noir 23 mai 2019 à 16:49:41

  • Partager sur Facebook
  • Partager sur Twitter
24 mai 2019 à 9:41:45

Je travail en fait sous visual studio, et j'ai essayé d'implementer ceci, dans un premier temps. Mais j'ai les erreur suivantes:

- erreur de syntaxe : absence de ',' avant '...'
- erreur de syntaxe : identificateur 'ARGS'

template<typename ...ARGS>
void Foo1(CString nam, ARGS... args) 
{
  // ...
}

Je ne comprends pas pourquoi j'ai ces erreurs.

Quelle différence cela fait si je remplace 'typename' par 'class' ? Si je remplace, j'ai ces deux erreur qui s'ajoute :

- 'class' : nom de balise manquant
- '<unnamed-tag>' : redéfinition du type 'enum'

-
Edité par adrien050356 24 mai 2019 à 9:45:13

  • Partager sur Facebook
  • Partager sur Twitter
24 mai 2019 à 11:10:30

il faut un espace entre ARGS et les ...
  • Partager sur Facebook
  • Partager sur Twitter
Ce qui se conçoit bien s'énonce clairement. Et les mots pour le dire viennent aisément.Mon nouveau livre : Coder efficacement - Bonnes pratiques et erreurs  à éviter (en C++)Avant de faire ce que tu ne pourras défaire, penses à tout ce que tu ne pourras plus faire une fois que tu l'auras fait
24 mai 2019 à 11:34:13

J'ai essayé toute les façon de l'écrire. Et je trouve toute sorte d'exemple sur internet avec et sans espace.

Je me suis renseigné, et visiblement Visual Studio 2012 ne gère pas les template variadic. Il y a bien un plug-in a jouter, mais il ne compile pas, dû à la config de mon projet.

-
Edité par adrien050356 24 mai 2019 à 11:36:10

  • Partager sur Facebook
  • Partager sur Twitter
24 mai 2019 à 12:15:02

La norme interdit formellement l'utilisation de classes avant les "...", donc `f(CString, ...)` est interdit par la norme.

Ensuite, si tu dois rester en C, il est alors nécessaire que tu disposes d'une surcharge qui accepte des `va_list`.

Bref à défaut de pouvoir migrer vers une compilateur non antédiluvien, tu me sembles coincé.

  • Partager sur Facebook
  • Partager sur Twitter
C++: Blog|FAQ C++ dvpz|FAQ fclc++|FAQ Comeau|FAQ C++lite|FAQ BS| Bons livres sur le C++| PS: Je ne réponds pas aux questions techniques par MP.
24 mai 2019 à 14:17:11

En effet j'avais pas pensé à surcharger ma fonction. Je viens de le faire et ça marche :)

Bon c'est pas parfait mais mais ça me permet d'avancer.

merci

  • Partager sur Facebook
  • Partager sur Twitter
6 juin 2019 à 19:09:51

VS2019 Community Edition est "gratuit" et support les variadic template, normalement.
  • Partager sur Facebook
  • Partager sur Twitter
Je recherche un CDI/CDD/mission freelance comme Architecte Logiciel/ Expert Technique sur technologies Microsoft.