IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Langage C++ Discussion :

Le mot clef auto


Sujet :

Langage C++

  1. #1
    Membre expérimenté Avatar de ctxnop
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juillet 2007
    Messages
    858
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2007
    Messages : 858
    Points : 1 732
    Points
    1 732
    Par défaut Le mot clef auto
    Bonjour,
    Il semble y avoir un sorte de consensus global (beaucoup d'experts de beaucoup de langages différents) sur le fait qu'il serait préférable d'utiliser le mot clef "auto" (ou équivalent dans les autres langages) plutôt que de typer directement "à l'ancienne".
    Je comprend tout à fait l'utilité dans certains cas, notamment quand les noms de types deviennent extrêmement longs à cause des templates par exemple.
    Cependant je reste frileux sur le sujet. J'ai la conviction que l'utilisation systématique de cette fonctionnalité entraine des situations où un refactoring changera la sémantique sans que ça ne provoque d'erreur de compilation. Et cette situation me déplait fortement.
    Exemple :
    Code c++ : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    int getLastDocumentCode() { return 12; }
     
    void saveDocument()
    {
        auto lastDocumentCode = getLastDocumentCode();
        lastDocumentCode = lastDocumentCode + 1;
        auto documentId = "DC"s + lastDocumentCode;
    }

    Dans ce code on s'attend à ce que documentId soit égal à "DC13". Mais si jamais on fait un refactoring pour avoir std::string getLastDocumentCode() { return "12"s; }, alors documentId sera égal à "DC121".
    La sémantique à changée et pourtant le compilo n'a rien dit. Alors évidement, le code est loin d'être parfait, mais ce n'est qu'un exemple. Et puis de toute façon, dans la vrai vie, les codes qu'on se traines depuis des années sont très très loin d'être parfaits...
    En attendant, si lastDocumentCode avait été typé "int", le changement d'interface aurait provoqué une erreur de compilation, ce qui me satisfait plus que de compter sur l'exhaustivité des tests pour éviter que le problème ne soit découvert en prod...

    Ai-je raison de penser ça ? Ou l'exemple donné (que je n'ai pas testé) est trop bidon et ne peut se produire réellement ? Peut-on vraiment mettre auto partout ?
    D'un point de vue plus personnel je trouve que ça nuit à la lisibilité de ne plus voir les types, être obligé d'avoir un IDE et de mettre son curseur sur la variable pour savoir ce qu'a "deviné" le compilo...

  2. #2
    Membre confirmé Avatar de KsassPeuk
    Homme Profil pro
    Ingénieur Chercheur
    Inscrit en
    Juillet 2013
    Messages
    138
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur Chercheur
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2013
    Messages : 138
    Points : 635
    Points
    635
    Par défaut
    Lu'!

    La tendance tire vers almost always auto.

    Il y a une partie à ne pas négliger c'est qu'une part de ton travail est d'assurer que le type que tu vas manipuler correspond à ce que tu attends. Déjà en ce qui me concerne, je n'aime pas vraiment l'exemple parce que typiquement un code, c'est un truc qui est sensé avoir un format, ce qui à mon sens justifie d'avoir un type spécialisé. L'autre raison pour laquelle je n'aime pas trop cet exemple, c'est qu'il ne pointe pas un problème avec auto mais un problème avec std::string. Le symbole "+" pour la concaténation, c'était pas franchement l'idée du siècle (et oui, plein de langages le font, et non, c'est pas une raison pour faire pareil), en même temps on ne peut pas définir n'importe quoi comme étant une notation en C++ donc c'était le mieux qu'on puisse faire.

    Pour le auto dans les blocs, j'ai tendance à dire :
    • Inférence dans la majorité des cas
    • typage manuel quand on a besoin d'un type précis pour respecter son contrat
    • typage manuel pour la création d'une variable sans dépendance


    Pour le auto dans les paramètres/retour de fonction :
    • quand la sémantique de la fonction est très claire
    • et que le contrat des types qu'elle reçoit/retourne est évident


    Citation Envoyé par ctxnop Voir le message
    D'un point de vue plus personnel je trouve que ça nuit à la lisibilité de ne plus voir les types, être obligé d'avoir un IDE et de mettre son curseur sur la variable pour savoir ce qu'a "deviné" le compilo...
    Normalement, une bonne fonction, c'est une fonction courte avec un accès restreint au scope, ce qui veut dire que la déclaration des éléments qu'on utilise ne doit globalement pas se trouver bien loin : soit c'est un paramètre, soit ça fait parti de l'objet qu'on manipule (donc on a son header ouvert pas trop loin), soit c'est un retour de fonction dont on connaît le type de retour. L'autre chose c'est qu'un code clair utilise des noms clairs, donc a priori le nom de la variable doit nous en dire autant, sinon plus, à son sujet que son type.

  3. #3
    Membre éclairé

    Profil pro
    Inscrit en
    Décembre 2013
    Messages
    393
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2013
    Messages : 393
    Points : 685
    Points
    685
    Par défaut
    Dans l'absolu, ton code d'exemple n'est pas faux.

    Mais normalement, il ne faudrait pas faire comme cela (a mon avis). Tu as un document qui possède un code et qui être sauvegardé. Donc il faudrait avoir une classe document qui possède une fonction save.
    L'autre problème est que retourner un code est équivalent a avoir un getter et donc (petite) violation de Demeter.
    Au final, le problème est que tu as un code qui dépend du type de "code", mais qui est séparé dans 2 endroits différents (perte de localité de l'information). Cela implique que celui qui modifie le code de "document" doit vérifier aussi que le code client utilise correctement la classe "document", ce qui ne devrait pas avoir lieu. Si ces 2 informations sont co-localisées dans la même classe, celui qui modifie la classe document ne doit vérifier que la cohérence de ses changements dans la classe "document", pas dans le code client.

    Bref, c'est pas faux dans le sens ou l'on voit souvent ce type de code dans un programme réel, mais c'est un problème de conception a la base (qui a pour conséquence de diminuer la robustesse du code = le code est sensible aux changements, comme on peut le voir dans ton exemple)

  4. #4
    Membre expérimenté Avatar de ctxnop
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juillet 2007
    Messages
    858
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2007
    Messages : 858
    Points : 1 732
    Points
    1 732
    Par défaut
    Tout d'abord, merci de vos participations.

    Cependant je pense que vous vous attachez trop à l'exemple.
    J'ai pris l'exemple d'un string parce que c'est standard et donc c'est déjà ce qui est fait à beaucoup d'endroits. Mais le problème reste entier avec tout le reste des codes. J'ai utilisé l'opérateur + ici, mais on peut tout à fait imaginer une méthode classique qui poserait le même problème. Après tout les opérateurs ne sont que des méthodes comme les autres. Je suis persuadé qu'on peut faire un exemple qui respecte tous les préceptes d'un code de qualité et qui pourtant provoque le problème.

    Je suis on ne peut plus d'accord pour dire que les règles de bonnes pratiques disent qu'on fait des fonctions qui prennent le moins de paramètres possible, qui ne doivent pas faire 500 lignes, qu'on nomme les variables correctement, etc...
    Mais croire que c'est respecté partout, tout le temps, par tout le monde, c'est juste utopique. Et ce dans quelque langage que ce soit.

    De mon point de vue, pousser à l'utilisation en toute circonstance, "les yeux fermés", à l'utilisation d'une fonctionnalité qui induit un risque dans la vie des codes existant ou des codes qui ne sont pas parfaits en terme de propreté, ce n'est pas judicieux. J'ai regardé de nombreuses conférences sur le sujet, lu beaucoup d'article ou tuto, etc... et pas une fois le problème n'est évoqué.

    Savoir que "count" est une variable "int" parce qu'elle est déclarée "auto count = 12;" je suis tout à fait d'accord qu'il n'y avait pas besoin de la typer "int" explicitement. Cependant si elle est déclarée "auto count = getCount();" comment je sais quel est son type réel au premier coup d'oeil ? Je sais que c'est très probablement un int vu le nom, mais ca pourrait être un unsigned int, un long, un short, ou je ne sais quoi d'autre. A moins d'avoir la fonction getCount() sous les yeux je ne peux pas être certain du type dans "demander" au compilo ou sans aller voir la définition de getCount(). Dans tous les cas c'est plus lourd à faire que de lire "int count = getCount();".
    On peut argumenter sur le fait que je n'ai peut être pas à le savoir, ou que c'est pas propre de faire comme ça, ou je ne sais quoi, mais la réalité c'est que ces codes font partis de nos quotidien et il faut bien faire avec.

    Puisqu'il y a des cas, relativement nombreux, où "auto" n'apporte absolument rien et/ou que le typage classique est plus lisible, pour être cohérent j'aurais tendance à toujours tout typer de la même façon, partout. Et donc j'aurais tendance à typer classiquement. Les seuls cas où je trouve qu'auto à de l'intérêt c'est lorsque le type devient trop long du genre std::vector<int>::const_iterator.

    PS: j'ai édité vu qu'une réponse s'est insérée entre la mienne et la première réponse

  5. #5
    Membre éclairé

    Profil pro
    Inscrit en
    Décembre 2013
    Messages
    393
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2013
    Messages : 393
    Points : 685
    Points
    685
    Par défaut
    Oui, tu as raison pour le support du code existant. L'utilisation de auto (AAA) nécessite au préalable que le code soit robuste. Il serait dangereux de faire les choses a moitié, c'est a dire de passer tout a auto sur un code mal conçu.
    Mais ceux qui préconiseur le AAA prêche aussi pour la bonne conception, donc tout va bien.

  6. #6
    Expert éminent sénior

    Femme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2007
    Messages
    5 189
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 5 189
    Points : 17 141
    Points
    17 141
    Par défaut
    Sauf que le type de bidule.getCount(), ce n'est ni int, ni short, ni long, mais Bidule::size_type.

    Un auto, c'est un type du bon type, qui sert, non pas à toi développeur, mais bien au compilateur.
    Toi, tu n'as pas besoin de savoir ce que c'est comme type.

    Ici, j'ai par exemple envie de pouvoir boucler, et j'aurai donc:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    for (auto i=0, end = bidule.getCount(); i!=end; ++i) {
        stream << "l'élément "<<i<<" est " << bidule(i) <<'\n';
    }
    Je veux seulement que i et end soit du même type (d'où la déclaration sur le même auto), et soit ++able.
    Ca pourrait parfaitement être un ptrdiff_t ou un iterateur magiquement convertible en unsigned short.

    Les types ne servent vraiment qu'aux paramètres et aux membres des classes.
    Et en général, je colle des typedef de partout.

    Pour deux raisons:
    la première est une considération pratique, je peux passer à une template, ou en revenir, sans grand effort.
    La seconde est sémantique: je veux que les types soit nommés selon leurs utilisations, pas leurs formes.

    Pour une date, j'aurais trois types de bases (day_type, month_type, year_type), et des types complémentaires (tels que difference_type).
    En fait, la présence d'un type primitif (hors bool) dans l'interface publique de mes fonctions me fait systématiquement réfléchir.

    Par contre, pour tout ce qui est privé (implémentation, etc), auto est largement suffisant.
    De toute façon, comme je fais en sorte de maximiser les chainages, et de limiter au maximum la taille des fonctions, je n'ai quasiment jamais de variables locales.
    Sauf des auto const& pour les boucles.

    Je peux raisonnablement dire que 90% de mes fonctions ne contiennent pas de variables locales.

    Et quand c'est le cas, ca donne des choses telles que (extrait de mémoire du démineur que je code pour m'exercer sur la SFML):
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    public:
        bool jouer(position_type const& p) {
            if (!valid(p) || !at(p).accepts(current()) ) return false;
            activate(p);
            return true;
        }
     
    private:
        void activate(position_type const& p) {
            auto& here = at(p);
            if (here.seen()) return;
            here.activate();
            if (here.empty()) {
                for(auto shift : neighbours()) {
                    auto there = p+shift;
                    if (valid(there)) activate(there);
                }
            }
        }
        static std::vector<shift_type> neighbours() {
            return {{-1,-1}, {-1, 0},/**/};
        }
    trois fonctions, trois temporaire, et encore, il y en a une pour éviter de calculer deux fois une somme entre une position et un décalage.
    Je n'ai pas une seule fois besoin des types réels, seulement de nommer des informations que j'utilise (position actuelle, décalage dans la grille, etc).

    Si je passe à un démineur en 3, 4 ou 17D, je n'ai que deux choses à changer: les typedef (position_type et shift_type, et neighbours).
    (par contre, pour l'interface graphique en 17D, ca va être plus galère )
    Mes principes de bases du codeur qui veut pouvoir dormir:
    • Une variable de moins est une source d'erreur en moins.
    • Un pointeur de moins est une montagne d'erreurs en moins.
    • Un copier-coller, ça doit se justifier... Deux, c'est un de trop.
    • jamais signifie "sauf si j'ai passé trois jours à prouver que je peux".
    • La plus sotte des questions est celle qu'on ne pose pas.
    Pour faire des graphes, essayez yEd.
    le ter nel est le titre porté par un de mes personnages de jeu de rôle

  7. #7
    Membre éclairé

    Profil pro
    Inscrit en
    Décembre 2013
    Messages
    393
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2013
    Messages : 393
    Points : 685
    Points
    685
    Par défaut
    (using, plus typedef )

  8. #8
    Expert éminent sénior

    Femme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2007
    Messages
    5 189
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 5 189
    Points : 17 141
    Points
    17 141
    Par défaut
    Citation Envoyé par mintho carmo Voir le message
    (using, plus typedef )
    Je dis encore typedef, parce que les gens comprennent mieux.
    Mais j'essaie de coder avec using
    Mes principes de bases du codeur qui veut pouvoir dormir:
    • Une variable de moins est une source d'erreur en moins.
    • Un pointeur de moins est une montagne d'erreurs en moins.
    • Un copier-coller, ça doit se justifier... Deux, c'est un de trop.
    • jamais signifie "sauf si j'ai passé trois jours à prouver que je peux".
    • La plus sotte des questions est celle qu'on ne pose pas.
    Pour faire des graphes, essayez yEd.
    le ter nel est le titre porté par un de mes personnages de jeu de rôle

  9. #9
    Membre expérimenté Avatar de ctxnop
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juillet 2007
    Messages
    858
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2007
    Messages : 858
    Points : 1 732
    Points
    1 732
    Par défaut
    Mouais, autant je comprends très bien tout que vous me dites, autant je ne suis toujours pas convaincu par l'utilisation quasi systématique d'auto.
    J'ai vraiment l'impression que les arguments qu'on m'opposent se concentrent sur l'exemple au lieu de se concentrer sur le problème posé.

  10. #10
    Rédacteur/Modérateur
    Avatar de JolyLoic
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2004
    Messages
    5 463
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2004
    Messages : 5 463
    Points : 16 213
    Points
    16 213
    Par défaut
    Mon avis par rapport à ça, c'est qu'il y a effectivement des cas où l'utilisation d'auto plutôt que d'un type précis cachera des bugs lors d'un refactoring. Mais il y a aussi des cas où l'utilisation d'un type précis plutôt que d'auto cachera des bugs lors d'un refactoring.

    Donc la question n'est pas tant "est-ce qu'une solution est parfaite", mais plus "est-ce qu'une solution produit significativement plus de soucis qu'une autre". C'est un genre de question assez difficile à répondre, mais je pense qu'utiliser auto causera globalement moins de soucis qu'utiliser des types précis. Parce que que auto va être meilleur sur les changements "techniques" (int => size_t), et moins bon sur les changements "sémantiquement" (int => string), et que je pense que la plupart des refactorings sont avant tout "techniques".
    Ma session aux Microsoft TechDays 2013 : Développer en natif avec C++11.
    Celle des Microsoft TechDays 2014 : Bonnes pratiques pour apprivoiser le C++11 avec Visual C++
    Et celle des Microsoft TechDays 2015 : Visual C++ 2015 : voyage à la découverte d'un nouveau monde
    Je donne des formations au C++ en entreprise, n'hésitez pas à me contacter.

  11. #11
    Membre expérimenté Avatar de ctxnop
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juillet 2007
    Messages
    858
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 39
    Localisation : France, Morbihan (Bretagne)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juillet 2007
    Messages : 858
    Points : 1 732
    Points
    1 732
    Par défaut
    Je ne vois pas trop comment l'utilisation d'un type précis plutôt qu'auto peut induire un problème (un petit exemple ? ). Mais effectivement, dans ce cas il faut choisir la solution la moins pire.
    Bon bah j'ai plus qu'a tenter de me forcer a l'utiliser.

  12. #12
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 519
    Points
    41 519
    Par défaut
    Je ne suis pas sûr que le gain en refactoring soit suffisant pour compenser la perte de lisibilité d'un tel code:
    Code C++11 : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    auto a = getA();
    auto b = getB();
    auto c = Function(a, b);
    Fonction(c);

    D'un autre côté, la notation hongroise peut aider ici, déplaçant l'information manquante vers le nom de la variable... du moment que les gens ne se mettent pas à utiliser a comme préfixe.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  13. #13
    Membre éclairé

    Profil pro
    Inscrit en
    Décembre 2013
    Messages
    393
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Décembre 2013
    Messages : 393
    Points : 685
    Points
    685
    Par défaut
    Le problème de ce code n'est pas l'utilisation de auto, mais le fait que les fonctions sont mal nommées

    Quand tu écris auto i = 0;, tu as l'information du type dans la même ligne que le auto. Quand tu écris auto it = begin(v) idem. Idem avec make_shared, make_unique, etc. Avec getCount, tu sais que tu as un compte (donc un entier).
    Bref, à chaque fois, tu connais le type, ou tout au moins tu as suffisamment d'information sur le type pour le manipuler (begin = c'est un pointeur, count = c'est un entier, etc)

    C'est améliorable (en particulier avec les concepts, qui permettront de vérifier directement que l'on a affaire à un BidirectionalIterator ou un UnidirectionalIterator - mais on peut ajouter une ligne après le auto pour vérifier avec static_assert que le type est correct), mais auto fait correctement son boulot (mais pas plus = si le contexte ne permet pas de comprendre le type manipulé, c'est pas auto qui donnera cette information)

  14. #14
    Rédacteur/Modérateur
    Avatar de JolyLoic
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2004
    Messages
    5 463
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 49
    Localisation : France, Yvelines (Île de France)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Août 2004
    Messages : 5 463
    Points : 16 213
    Points
    16 213
    Par défaut
    Citation Envoyé par ctxnop Voir le message
    Je ne vois pas trop comment l'utilisation d'un type précis plutôt qu'auto peut induire un problème (un petit exemple ? ). Mais effectivement, dans ce cas il faut choisir la solution la moins pire.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    vector<int> invert (vector<int> v)
    {
        unsigned long taille = v.size();
        vector<int> result(taille);
        for(unsigned long i = 0 ; i < taille ; ++i)
        {
            result[taille-i] = v[i];
        }
    }
    Sous windows, en 32 bits, ce code marche bien. Lors d'un refactoring vers 64 bits, ce code va mal marcher, mais uniquement pour des jeux de données trop grands (donc il passera les tests unitaires). Certes, le compilateur aura probablement mis un warning, mais dans une grande base de code ancien où il y en a déjà beaucoup... Avec auto, le code marche bien en 32 comme en 64 bits. Avec size_t, ou vector<int>::size_type aussi. Mais qu'est-ce qui me garanti que c'est bien le type utilisé ?
    Ma session aux Microsoft TechDays 2013 : Développer en natif avec C++11.
    Celle des Microsoft TechDays 2014 : Bonnes pratiques pour apprivoiser le C++11 avec Visual C++
    Et celle des Microsoft TechDays 2015 : Visual C++ 2015 : voyage à la découverte d'un nouveau monde
    Je donne des formations au C++ en entreprise, n'hésitez pas à me contacter.

  15. #15
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 519
    Points
    41 519
    Par défaut
    Euh, là tu peux déclarer taille en auto, mais pas i...

    Je vais de ce pas ajouter -Dschtroumpf=auto dans mes lignes de commande de compilation.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  16. #16
    Expert éminent sénior

    Femme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2007
    Messages
    5 189
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 5 189
    Points : 17 141
    Points
    17 141
    Par défaut
    C'est l'intéret d'écrire for(unsigned long i = 0, taille = v.size() ; i < taille ; ++i).
    Avec auto ou un type explicite, comme i et taille sont déclarés ensembles, ils sont forcément de même type.

    C'est d'ailleurs comme ca que tu verras les boucles écrites dans boost ou dans la STL de gcc

    Comme il s'agit de déclarer i avec le même type que taille, une autre manière de procéder, ce serait d'utiliser decltype(taille).
    Mes principes de bases du codeur qui veut pouvoir dormir:
    • Une variable de moins est une source d'erreur en moins.
    • Un pointeur de moins est une montagne d'erreurs en moins.
    • Un copier-coller, ça doit se justifier... Deux, c'est un de trop.
    • jamais signifie "sauf si j'ai passé trois jours à prouver que je peux".
    • La plus sotte des questions est celle qu'on ne pose pas.
    Pour faire des graphes, essayez yEd.
    le ter nel est le titre porté par un de mes personnages de jeu de rôle

  17. #17
    Expert éminent sénior
    Avatar de Luc Hermitte
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Août 2003
    Messages
    5 275
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Août 2003
    Messages : 5 275
    Points : 10 985
    Points
    10 985
    Par défaut
    Citation Envoyé par ctxnop Voir le message
    Je ne vois pas trop comment l'utilisation d'un type précis plutôt qu'auto peut induire un problème (un petit exemple ? ).
    C'est dans la même idée que le code donné par Loic: http://ewontfix.com/9/

    Citation Envoyé par Médinoc Voir le message
    D'un autre côté, la notation hongroise peut aider ici, déplaçant l'information manquante vers le nom de la variable... du moment que les gens ne se mettent pas à utiliser a comme préfixe.
    Oh pitié, le retour de la notation hongroise système serait un enfer. Au refactoring, je pense que c'est la pire situation de toutes. Imaginez aussi un peu un "auto iSize=v.size();" à un endroit et un "ullWeigth" ailleurs. On arrive vite à des incohérences. Sans parler, de que fait-on quoi pour les objets ? Petit o ?
    Non, on n'a pas besoin de ça. Même avec auto. Gardez vos fonctions courtes, et cela ira bien.

    Ce qui me fait penser : en cas d'application bien utile, il y a les codes C++ générés automatiquement à partir de schema xsd. Il me serait bien pratique d'utiliser auto plutôt que des types imbriqués (à coup de typedefs) de 3km de long.
    Blog|FAQ C++|FAQ fclc++|FAQ Comeau|FAQ C++lite|FAQ BS|Bons livres sur le C++
    Les MP ne sont pas une hotline. Je ne réponds à aucune question technique par le biais de ce média. Et de toutes façons, ma BAL sur dvpz est pleine...

  18. #18
    Expert éminent

    Inscrit en
    Novembre 2005
    Messages
    5 145
    Détails du profil
    Informations forums :
    Inscription : Novembre 2005
    Messages : 5 145
    Points : 6 911
    Points
    6 911
    Par défaut
    Citation Envoyé par Médinoc Voir le message
    Je ne suis pas sûr que le gain en refactoring soit suffisant pour compenser la perte de lisibilité d'un tel code:
    Code C++11 : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    auto a = getA();
    auto b = getB();
    auto c = Function(a, b);
    Fonction(c);
    Le probleme de lisibilite n'est en rien lie a auto.

    Code c++11 : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    A a = getA();
    B b = getB();
    C c = Function(a, b);
    Function(c);

    n'est en rien plus lisible. Donner des noms significatifs va regler le probleme de lisibilite dans les deux cas. Sauf pour les cas de template a rallonge ou de conversion implicite (avec des expressions templates, le type desire est rarement celui que fournit auto, ou meme auto&&).
    Les MP ne sont pas là pour les questions techniques, les forums sont là pour ça.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Intérêt du mot-clef 'auto'
    Par Boumbata dans le forum Langage
    Réponses: 6
    Dernier message: 11/06/2014, 14h58
  2. mot-clef static
    Par keil dans le forum C++
    Réponses: 8
    Dernier message: 25/01/2006, 17h11
  3. Variables automatiques et mot clé auto, variables register.
    Par Évariste Galois dans le forum C++
    Réponses: 6
    Dernier message: 11/08/2005, 20h30
  4. mot clef sql pour nom de champ
    Par bobinou007 dans le forum Langage SQL
    Réponses: 4
    Dernier message: 12/10/2004, 13h21

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo