de nombreux logiciels imposent l'utilisation d'un C++ allégé (sans templates, sans héritage multiple, sans pointeurs nus...)
Ils en interdisent rarement la totalité des exemples, mais un jeu (encore que, je n'ai jamais vu les pointeurs nus être interdits).
Perso, je sais que dans mes projets j'essaie d'éviter d'utiliser les exceptions par exemple: tout bêtement parce qu'il n'existe aucun moyen à ma connaissance de s'assurer qu'elles sont toutes gérées correctement (non, try{}catch(...){abort();} après 10 niveaux d'encapsulation ou rien n'est attrapé, ce n'est pas une façon correcte de le faire), et que donc ça reviens à un printf("j'ai glissé chef!\n");abort(); (voire pire, parce qu'on ne sait même pas dans quel fichier et à quel ligne les choses ont commencé à merder).
Mais pas de bol, le C++ malgré son "you pay for what you use" ne fournit aucun conteneur «semi-dynamique» (qui ne grossisse pas de façon implicite, histoire que l'on ait une chance d'éviter les crash parce que le kernel à attribué de la mémoire qu'il n'a pas réservée en réalité) ou exception-free, donc si je veux utiliser la STL, je l'ai dans l'os (sauf à ré-implémenter mes propres conteneurs, forcément, ce qui n'est pas nécessairement difficile mais pénible) sur ce point.
Du coup, bah je n'utilise pas les exceptions tout en sachant que mon code peut exploser parce que les outils dont je dépend eux en utilisent éventuellement (ça peut être une lib qui en utilise une alors que la doc n'a pas été mise à jour, par exemple).
les templates bien utilisés permettent d'éviter la duplication de code, et en améliorent la maintenabilité
J'invoque les 2 implémentations de la STL (seul outil dont je ne puisse me passer qui utilise réellement les template à fond) avec lesquels j'ai le plus travaillé en contre-exemple: libstdc++ et libcpp.
Tu serais vraiment très, très fort si tu arrivais à me convaincre que ces trucs sont maintenables grâce aux templates (avec mention spéciale pour la libstdc++ qui est vraiment, vraiment dégueulasse, un simple appel à size() fait passer par une chiée de fonctions dont l'indentation est un mélange d'espaces et de tabulations!).
Il me faut aussi mentionner le fait que les compilateurs que j'utilisent (g++ et clang) optimisent même en -O0 -g les templates, rendant ingérable le debug sans connaître les mécanismes internes (bien qu'il faille reconnaître ici qu'au moins libstdc++ fournit une solution de contournement pour gdb, si on a python3 disponible) ainsi que le fait que l'endroit qui génère une erreur de compilation est toujours noyé dans 2 pages de diagnostic (au moins, avec clang, on arrive à s'y retrouver grâce aux couleurs, mais ça reste sous-optimal) qui sont souvent tout sauf pertinents.
Alors, c'est vrai, tu as précisé «bien utilisés», mais du coup, aurais-tu des exemples de code, post C++11 (enfin, si t'en trouves du pré C++11 tu auras encore plus mon respect) qui n'ait pas ces problèmes d'utilisation?
Honnêtement, dans le fond, je suis relativement d'accord (j'ai quelques utilitaires templates qui sont bien utiles pour libérer automatiquement des ressources sans overhead (chose que la STL ne sait pas faire), mais sincèrement, selon moi pour qu'un template rende du code maintenable il ne faut pas abuser des fonctionnalités qu'ils offrent. Avec mention spéciale pour la récursion et donc les variadic. Je ne dis pas que ça n'a aucun intérêt, mais quand on on arrive à faire ça pour un switch, à part pour le fun, j'ai un sérieux doute.
Peut-être que le switch est plus lisible, mais si pour détecter un bug même trivial il faut passer 2 heures à éplucher des indirections...
*: au sujet des conteneurs pénibles:
devoir implémenter operator== quand operator!= l'est (pour rappel: il y 10 opérateurs de comparaison au total, qui peuvent s'implémenter avec 2 seulement!), et le seul intérêt «réel» de les implémenter séparément que je vois, c'est pour obfusquer le code et le rendre plus buggué, peut-être pour un futur IOCPPCC?
idem pour les divers opérateurs d'accès dans leurs formes const/non-const
idem pour les itérateurs, bien que le jour ou je suis tombé sur un article mentionnant l'idée de passer un paramètre template booléen pour la constance à changé ma vie. Je ne m'emmerde jamais à utiliser et encore moins implémenter les reverse iterators, j'ai autre chose à faire qu'écrire du boilerplate après tout.
[^] # Re: Namespace bits ?
Posté par freem . En réponse au journal Jouons avec le ``switch`` et C++17. Évalué à 5.
Ils en interdisent rarement la totalité des exemples, mais un jeu (encore que, je n'ai jamais vu les pointeurs nus être interdits).
Perso, je sais que dans mes projets j'essaie d'éviter d'utiliser les exceptions par exemple: tout bêtement parce qu'il n'existe aucun moyen à ma connaissance de s'assurer qu'elles sont toutes gérées correctement (non,
try{}catch(...){abort();}après 10 niveaux d'encapsulation ou rien n'est attrapé, ce n'est pas une façon correcte de le faire), et que donc ça reviens à unprintf("j'ai glissé chef!\n");abort();(voire pire, parce qu'on ne sait même pas dans quel fichier et à quel ligne les choses ont commencé à merder).Mais pas de bol, le C++ malgré son "you pay for what you use" ne fournit aucun conteneur «semi-dynamique» (qui ne grossisse pas de façon implicite, histoire que l'on ait une chance d'éviter les crash parce que le kernel à attribué de la mémoire qu'il n'a pas réservée en réalité) ou exception-free, donc si je veux utiliser la STL, je l'ai dans l'os (sauf à ré-implémenter mes propres conteneurs, forcément, ce qui n'est pas nécessairement difficile mais pénible) sur ce point.
Du coup, bah je n'utilise pas les exceptions tout en sachant que mon code peut exploser parce que les outils dont je dépend eux en utilisent éventuellement (ça peut être une lib qui en utilise une alors que la doc n'a pas été mise à jour, par exemple).
J'invoque les 2 implémentations de la STL (seul outil dont je ne puisse me passer qui utilise réellement les template à fond) avec lesquels j'ai le plus travaillé en contre-exemple: libstdc++ et libcpp.
Tu serais vraiment très, très fort si tu arrivais à me convaincre que ces trucs sont maintenables grâce aux templates (avec mention spéciale pour la libstdc++ qui est vraiment, vraiment dégueulasse, un simple appel à
size()fait passer par une chiée de fonctions dont l'indentation est un mélange d'espaces et de tabulations!).Il me faut aussi mentionner le fait que les compilateurs que j'utilisent (g++ et clang) optimisent même en
-O0 -gles templates, rendant ingérable le debug sans connaître les mécanismes internes (bien qu'il faille reconnaître ici qu'au moins libstdc++ fournit une solution de contournement pour gdb, si on a python3 disponible) ainsi que le fait que l'endroit qui génère une erreur de compilation est toujours noyé dans 2 pages de diagnostic (au moins, avec clang, on arrive à s'y retrouver grâce aux couleurs, mais ça reste sous-optimal) qui sont souvent tout sauf pertinents.Alors, c'est vrai, tu as précisé «bien utilisés», mais du coup, aurais-tu des exemples de code, post C++11 (enfin, si t'en trouves du pré C++11 tu auras encore plus mon respect) qui n'ait pas ces problèmes d'utilisation?
Honnêtement, dans le fond, je suis relativement d'accord (j'ai quelques utilitaires templates qui sont bien utiles pour libérer automatiquement des ressources sans overhead (chose que la STL ne sait pas faire), mais sincèrement, selon moi pour qu'un template rende du code maintenable il ne faut pas abuser des fonctionnalités qu'ils offrent. Avec mention spéciale pour la récursion et donc les variadic. Je ne dis pas que ça n'a aucun intérêt, mais quand on on arrive à faire ça pour un switch, à part pour le fun, j'ai un sérieux doute.
Peut-être que le switch est plus lisible, mais si pour détecter un bug même trivial il faut passer 2 heures à éplucher des indirections...
*: au sujet des conteneurs pénibles:
operator==quandoperator!=l'est (pour rappel: il y 10 opérateurs de comparaison au total, qui peuvent s'implémenter avec 2 seulement!), et le seul intérêt «réel» de les implémenter séparément que je vois, c'est pour obfusquer le code et le rendre plus buggué, peut-être pour un futur IOCPPCC?