Partage
  • Partager sur Facebook
  • Partager sur Twitter

Lambda

    22 juillet 2019 à 14:03:06


    Bonjour,

    Je suis le cours C++, un code m'intrigue ?


    #include <algorithm>
    #include <array>
    #include <iostream>
    
    int main()
    {
        std::array<double, 4u> tableau { 1, 3.1415, 2.1878, 1.5 };
    
        // Tri dans l'ordre décroissant.
        std::sort(std::begin(tableau), std::end(tableau), [](double a, double b) -> double
        {
            return a > b;
        });
    
        for (auto nombre : tableau)
        {
            std::cout << nombre << std::endl;
        }
    
        return 0;
    }

    Pourquoi il mettent le type de retour de la Lambda en double ?


    • Partager sur Facebook
    • Partager sur Twitter
      22 juillet 2019 à 14:54:01

      Sans contexte, difficile à dire, mais j'aurais tendance à dire que c'est une faute d'inattention.

      • Partager sur Facebook
      • Partager sur Twitter

      Posez vos questions ou discutez informatique, sur le Discord NaN | Tuto : Preuve de programmes C

        22 juillet 2019 à 17:21:37

        Peut être une confusion avec d'autres langages, où un comparateur est une fonction qui retourne un nombre dont le signe indique l'ordre. Et pour lequel la manière typique de comparer deux nombres est de retourner leur différence (return a - b);

        Whatever, ils se seraient économisés l'opportunité de faire une erreur en se reposant sur la déduction de types :

        auto ordreDecroissant = [](double a, double b) { return a > b; };
        
        std::sort(std::begin(tableau), std::end(tableau), ordreDecroissant);  
        


        ce qui gagnerait aussi en lisibilité, rendant le commentaire parfaitement inutile.

        • Partager sur Facebook
        • Partager sur Twitter
          22 juillet 2019 à 17:53:37

          Il ne faut pas hésiter à signaler ce genre d'erreur directement sur la discussion sur le forum ZdS, pour que les auteurs puissent corriger le cours. (Je leur ai signalé cette discussion)

          @Michel C'est un choix de la part des auteurs, comme indiqué au début du chapitre :

          Le type de retour : encore un élément qui nous est 
          familier. Il est écrit après la flèche ->. Il peut être 
          omis dans quelques cas, mais nous allons l’écrire à chaque 
          fois dans une volonté d’écrire un code clair et explicite.

          Le chapitre en question : https://zestedesavoir.com/tutoriels/822/la-programmation-en-c-moderne/decoupons-tout-ca/des-fonctions-somme-toute-lambda/

          • Partager sur Facebook
          • Partager sur Twitter
          Pour poser des questions ou simplement discuter informatique, vous pouvez rejoindre le discord NaN.
            22 juillet 2019 à 18:26:36

            gbdivers a écrit:

            @Michel C'est un choix de la part des auteurs, comme indiqué au début du chapitre :

            Le type de retour : encore un élément qui nous est 
            familier. Il est écrit après la flèche ->. Il peut être 
            omis dans quelques cas, mais nous allons l’écrire à chaque 
            fois dans une volonté d’écrire un code clair et explicite.

            Le chapitre en question : https://zestedesavoir.com/tutoriels/822/la-programmation-en-c-moderne/decoupons-tout-ca/des-fonctions-somme-toute-lambda/

            L'enfer étant pavé de mauvaises intentions, il arrive fréquemment que le souhait d'être explicite aboutisse au résultat opposé en matière de clarté.

            Si on les prend au mot, il faudrait déclarer la variable comme

             std::function<bool(double,double)> ordreDecroissant = 
                  [](double a, double b) -> bool 
                     { 
                        return a > b; 
                     };
            
            

            C'est peut-être effrayés à la perspective d'avoir à écrire des choses aussi horribles (redondance) qu'ils ont préféré ne pas utiliser une variable auxiliaire pour le critère de comparaison, ce qui aurait pourtant été une excellente chose en terme de clarté et de maintenabilité du code.

             PS: question de curiosité, y a pas un moyen de dire que le paramètre, c'est  la version de  operator>  pour les doubles ?



            -
            Edité par michelbillaud 22 juillet 2019 à 18:35:16

            • Partager sur Facebook
            • Partager sur Twitter
              22 juillet 2019 à 18:33:55

              Attention, std::function n'est pas le type correct d'une lambda. Ton code est correct, mais il n'est pas exactement identique au code précédent. (Il y a un cast).

              Et de toute façon, dans le premier code, il n'y a pas de création de variable. Et le cours explique pourquoi il faut utiliser auto pour creer une variable qui recoit une lambda.

              EDIT:

              C'est peut-être effrayés à la perspective d'avoir à écrire
              des choses aussi horribles 

              Je ne pense pas. En termes pédagogiques, il est préférable de montrer les lambda utilisée directement dans un algo (pour montrer que le but est de les créer a la volée) et de montrer dans un second temps qu'on peut mettre une lambda dans une variable.

              PS: question de curiosité, y a pas un moyen de dire que le
               paramètre, c'est  la version de  operator>  pour les 
              doubles ?

              Pas compris ta question.

              -
              Edité par gbdivers 22 juillet 2019 à 18:38:17

              • Partager sur Facebook
              • Partager sur Twitter
              Pour poser des questions ou simplement discuter informatique, vous pouvez rejoindre le discord NaN.
                22 juillet 2019 à 18:48:52

                Pour dire que c'est l'opérateur de comparaison pour les doubles, il doit y avoir ça :

                std::greater<double>()


                https://en.cppreference.com/w/cpp/utility/functional/greater

                -
                Edité par anolya 22 juillet 2019 à 18:49:40

                • Partager sur Facebook
                • Partager sur Twitter
                  22 juillet 2019 à 19:21:17

                  Merci, Donc si je comprend bien, c'est bien une erreur, je pense que c'est bool le retour puisque c'est une comparaison qui est retournée.

                  J'ai aussi essayé en ne mettant pas le type de retour, ça marche aussi. C'est même moins perturbant. Parce que je l'ai regardé en plusieurs fois le code et j'avais l'impression de ne pas avoir compris. Ça ma mis le doute.

                  • Partager sur Facebook
                  • Partager sur Twitter
                    22 juillet 2019 à 19:35:18

                    @michel Je ne sais pas s'il y a un chapitre sur les prédicats fournis dans la lib standard. Si ce n'est pas le cas, tu peux leur suggérer d'ajouter un tel chapitre. Et peut etre ajouter une note dans ce chapitre pour dire qu'il serait préférable, dans un vrai code, d'utiliser std::greater plutot qu'une lambda.

                    Et peut etre que le chapitre n'insiste pas assez sur le fait qu'on peut souvent omettre le type de retour.

                    -
                    Edité par gbdivers 22 juillet 2019 à 19:36:15

                    • Partager sur Facebook
                    • Partager sur Twitter
                    Pour poser des questions ou simplement discuter informatique, vous pouvez rejoindre le discord NaN.
                      22 juillet 2019 à 20:59:55

                      MarcelPic a écrit:

                      Merci, Donc si je comprend bien, c'est bien une erreur, je pense que c'est bool le retour puisque c'est une comparaison qui est retournée.

                      J'ai aussi essayé en ne mettant pas le type de retour, ça marche aussi. C'est même moins perturbant. Parce que je l'ai regardé en plusieurs fois le code et j'avais l'impression de ne pas avoir compris. Ça ma mis le doute.


                      A partir du moment où un langage se met à autoriser des déductions de type et autres auto, on se retrouve avec un problème :

                      • dans le code existant, on est toujours explicite (pour cause)
                      • les vieux de la vieille, qui ont toujours fait comme ça, trouvent que c'est mieux de continuer à faire comme ça, parce que c'est mieux, et parce que tout le monde a fait comme ça jusque là, donc c'est mieux. et c'est comme ça.
                      • y en a quand même pour tirer partie des nouveautés.
                      • Mais dans le code, maintenant, il faut regarder chaque déclaration explicite avec un oeil inquisiteur. Est-elle explicite par tradition, ou parce que ce qui est déduit implicitement ne convient pas ?

                      -
                      Edité par michelbillaud 23 juillet 2019 à 9:06:55

                      • Partager sur Facebook
                      • Partager sur Twitter
                        22 juillet 2019 à 23:31:38

                        Je suis quasi sur qu'il n'y a pas cette erreur dans le cours C++ de OpenClassroom au moins :ange:

                        (oui car je suis à peu près sur que les lambda functions ne sont pas évoquées)

                        • Partager sur Facebook
                        • Partager sur Twitter

                        Recueil de codes en C et C++ http://fvirtman.free.fr/recueil/index.html

                          24 juillet 2019 à 8:35:56

                          Oui, je pense aussi qu’il n’ya pas d’erreur dans la classe ouverte. Et très probablement, ma pensée est correcte 

                          • Partager sur Facebook
                          • Partager sur Twitter

                          Lambda

                          × Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
                          • Editeur
                          • Markdown