Je cherche une solution pour le problème suivant. J'ai un objet A possédant
les méthodes f1 et f2. J'aimerais trier une liste de références sur des
objets de type A sur la valeur retournée par f1 ou par f2. Voici mon code :
...
$choix = "f1";
my @liste2 = sort { $a->$f1 cmp $b->$f1 } @liste1;
...
Evidemment cela ne fonctionne pas. Existe-t-il une solution propre pour
résoudre mon problème ?
Cette action est irreversible, confirmez la suppression du commentaire ?
Signaler le commentaire
Veuillez sélectionner un problème
Nudité
Violence
Harcèlement
Fraude
Vente illégale
Discours haineux
Terrorisme
Autre
Jean-Michel Caricand
Jean-Michel Caricand wrote:
Bonsoir,
Je cherche une solution pour le problème suivant. J'ai un objet A possédant les méthodes f1 et f2. J'aimerais trier une liste de références sur des objets de type A sur la valeur retournée par f1 ou par f2. Voici mon code :
...
$choix = "f1";
my @liste2 = sort { $a->$f1 cmp $b->$f1 } @liste1;
...
Evidemment cela ne fonctionne pas. Existe-t-il une solution propre pour résoudre mon problème ?
Merci.
J'ai fait une erreur dans mon code :-(
$choix = "f1";
my @liste2 = sort { $a->$choix cmp $b->$choix } @liste1;
Excusez moi.
Jean-Michel Caricand wrote:
Bonsoir,
Je cherche une solution pour le problème suivant. J'ai un objet A
possédant les méthodes f1 et f2. J'aimerais trier une liste de références
sur des objets de type A sur la valeur retournée par f1 ou par f2. Voici
mon code :
...
$choix = "f1";
my @liste2 = sort { $a->$f1 cmp $b->$f1 } @liste1;
...
Evidemment cela ne fonctionne pas. Existe-t-il une solution propre pour
résoudre mon problème ?
Merci.
J'ai fait une erreur dans mon code :-(
$choix = "f1";
my @liste2 = sort { $a->$choix cmp $b->$choix } @liste1;
Je cherche une solution pour le problème suivant. J'ai un objet A possédant les méthodes f1 et f2. J'aimerais trier une liste de références sur des objets de type A sur la valeur retournée par f1 ou par f2. Voici mon code :
...
$choix = "f1";
my @liste2 = sort { $a->$f1 cmp $b->$f1 } @liste1;
...
Evidemment cela ne fonctionne pas. Existe-t-il une solution propre pour résoudre mon problème ?
Merci.
J'ai fait une erreur dans mon code :-(
$choix = "f1";
my @liste2 = sort { $a->$choix cmp $b->$choix } @liste1;
Excusez moi.
Jean-Baptiste Mazon
Jean-Michel Caricand writes:
Je cherche une solution pour le problème suivant. J'ai un objet A possédant les méthodes f1 et f2. J'aimerais trier une liste de références sur des objets de type A sur la valeur retournée par f1 ou par f2. Voici mon code :
$choix = "f1";
my @liste2 = sort { $a->$choix cmp $b->$choix } @liste1;
A un détail près, ça marche chez moi. Il m'a toutefois été nécessaire de me livrer à une bonne dose d'extrapolation. Le bon usage demande que l'exemple de problème soit concis, certes, mais suffisant pour tourner de lui-même. Les détails de pourquoi ça ne marche pas ne sont pas de trop non plus (messages d'erreur, par exemple).
Déclarer un nom de fonction (ici méthode) dans une variable, ça s'appelle une référence symbolique. C'est déconseillé, obsolète, à éviter pour tout un tas de (bonnes) raisons, mais c'est encore censé marcher. Mais pour que Perl la retrouve, il lui faut quand même le nom du package où la trouver. Supposant "A", ça nous donne:
$choix = 'A::f1';
Débarrassons-nous tout de suite de la référence symbolique, dans notre cas ça ne change presque rien au code:
$choix = &A::f1;
Bon.
Malheureusement, cette manière de faire passe outre le dispatching: si quelqu'un dérive A et redéfinit f1, c'est malgré tout A::f1 qui se fera appeler.
Pour dispatcher et sur la méthode et sur la classe... je ne connais pas de solution Perl 5 qui reste concise. Il y a bien eval, mais c'est zéro en performances comme en maintenabilité. Si quelqu'un a une meilleure idée, je suis moi aussi preneur.
Un peu de code autosuffisant pour illustrer le tout:
#! perl -l
package A; sub key1 { substr ${$_[0]}, 0, 1 } # premiere lettre sub key2 { substr ${$_[0]}, -1 } # derniere lettre sub new { bless $_[1] }
package main;
@_ = map new A($_), qw(ceci est une liste de quelques mots);
print 'Tri par première lettre:'; print $$_ for sort { $a->key1 cmp $b->key1 } @_;
print 'Tri par dernière lettre:'; print $$_ for sort { $a->key2 cmp $b->key2 } @_;
print 'Tri par référence symbolique:'; # mais c'est Mal $_ = 'A::key1'; print $$_ for sort { $a->$_ cmp $b->$_ } @_;
Les syntaxes utilisées pour les tris par référence sont interchangeables. En l'occurrence, je préfère la seconde, qui illustre mieux où le dispatching a effectivement lieu.
Je cherche une solution pour le problème suivant. J'ai un objet A
possédant les méthodes f1 et f2. J'aimerais trier une liste de références
sur des objets de type A sur la valeur retournée par f1 ou par f2. Voici
mon code :
$choix = "f1";
my @liste2 = sort { $a->$choix cmp $b->$choix } @liste1;
A un détail près, ça marche chez moi. Il m'a toutefois été nécessaire
de me livrer à une bonne dose d'extrapolation. Le bon usage demande
que l'exemple de problème soit concis, certes, mais suffisant pour
tourner de lui-même. Les détails de pourquoi ça ne marche pas ne sont
pas de trop non plus (messages d'erreur, par exemple).
Déclarer un nom de fonction (ici méthode) dans une variable, ça
s'appelle une référence symbolique. C'est déconseillé, obsolète, à
éviter pour tout un tas de (bonnes) raisons, mais c'est encore censé
marcher. Mais pour que Perl la retrouve, il lui faut quand même le
nom du package où la trouver. Supposant "A", ça nous donne:
$choix = 'A::f1';
Débarrassons-nous tout de suite de la référence symbolique, dans notre
cas ça ne change presque rien au code:
$choix = &A::f1;
Bon.
Malheureusement, cette manière de faire passe outre le dispatching:
si quelqu'un dérive A et redéfinit f1, c'est malgré tout A::f1 qui se
fera appeler.
Pour dispatcher et sur la méthode et sur la classe... je ne connais
pas de solution Perl 5 qui reste concise. Il y a bien eval, mais
c'est zéro en performances comme en maintenabilité. Si quelqu'un a
une meilleure idée, je suis moi aussi preneur.
Un peu de code autosuffisant pour illustrer le tout:
#! perl -l
package A;
sub key1 { substr ${$_[0]}, 0, 1 } # premiere lettre
sub key2 { substr ${$_[0]}, -1 } # derniere lettre
sub new { bless $_[1] }
package main;
@_ = map new A($_), qw(ceci est une liste de quelques mots);
print 'Tri par première lettre:';
print $$_ for sort { $a->key1 cmp $b->key1 } @_;
print 'Tri par dernière lettre:';
print $$_ for sort { $a->key2 cmp $b->key2 } @_;
print 'Tri par référence symbolique:'; # mais c'est Mal
$_ = 'A::key1';
print $$_ for sort { $a->$_ cmp $b->$_ } @_;
Les syntaxes utilisées pour les tris par référence sont
interchangeables. En l'occurrence, je préfère la seconde, qui
illustre mieux où le dispatching a effectivement lieu.
Je cherche une solution pour le problème suivant. J'ai un objet A possédant les méthodes f1 et f2. J'aimerais trier une liste de références sur des objets de type A sur la valeur retournée par f1 ou par f2. Voici mon code :
$choix = "f1";
my @liste2 = sort { $a->$choix cmp $b->$choix } @liste1;
A un détail près, ça marche chez moi. Il m'a toutefois été nécessaire de me livrer à une bonne dose d'extrapolation. Le bon usage demande que l'exemple de problème soit concis, certes, mais suffisant pour tourner de lui-même. Les détails de pourquoi ça ne marche pas ne sont pas de trop non plus (messages d'erreur, par exemple).
Déclarer un nom de fonction (ici méthode) dans une variable, ça s'appelle une référence symbolique. C'est déconseillé, obsolète, à éviter pour tout un tas de (bonnes) raisons, mais c'est encore censé marcher. Mais pour que Perl la retrouve, il lui faut quand même le nom du package où la trouver. Supposant "A", ça nous donne:
$choix = 'A::f1';
Débarrassons-nous tout de suite de la référence symbolique, dans notre cas ça ne change presque rien au code:
$choix = &A::f1;
Bon.
Malheureusement, cette manière de faire passe outre le dispatching: si quelqu'un dérive A et redéfinit f1, c'est malgré tout A::f1 qui se fera appeler.
Pour dispatcher et sur la méthode et sur la classe... je ne connais pas de solution Perl 5 qui reste concise. Il y a bien eval, mais c'est zéro en performances comme en maintenabilité. Si quelqu'un a une meilleure idée, je suis moi aussi preneur.
Un peu de code autosuffisant pour illustrer le tout:
#! perl -l
package A; sub key1 { substr ${$_[0]}, 0, 1 } # premiere lettre sub key2 { substr ${$_[0]}, -1 } # derniere lettre sub new { bless $_[1] }
package main;
@_ = map new A($_), qw(ceci est une liste de quelques mots);
print 'Tri par première lettre:'; print $$_ for sort { $a->key1 cmp $b->key1 } @_;
print 'Tri par dernière lettre:'; print $$_ for sort { $a->key2 cmp $b->key2 } @_;
print 'Tri par référence symbolique:'; # mais c'est Mal $_ = 'A::key1'; print $$_ for sort { $a->$_ cmp $b->$_ } @_;
Les syntaxes utilisées pour les tris par référence sont interchangeables. En l'occurrence, je préfère la seconde, qui illustre mieux où le dispatching a effectivement lieu.