Je suis pourtant loin d'avoir exploré toutes les possibilités offertes, tellement elles sont énormes.
J'utilise principalement Perl pour ce quoi il est fait, c'est à dire analyser de la chaine pour en générer.
Les connaisseurs me demanderont pourquoi je ne code pas avec le langage que je défend : Je n'utilise pas encore Lisaac parce qu'il n'a pas encore de librairie regexp, et quand il en aura une, je m'occuperai très sérieusement de la lib standard de ce langage, dont les améliorations (de lib et de spec) que j'ai proposé sont encore essentiellement théorique pour l'instant.
Javouille, parce que non, je peux pas, je n'utilise ce langage que contraint et forcé, Java est tout sauf un langage intéressant (pas intégralement objet, pas de type block).
Je suis un fana des regexp, le seul bouquin d'informatique de ma bibliothèque s'y consacre intégralement. J'aime beaucoup plus généralement les langage où je défini mon besoin sans expliquer comment y parvenir, les regexp sont très proches de cet idiome, ainsi que SQL.
Je me suis donc attelé à produire une petite liste de choses que j'ai aimé, qui m'ont surpris dans ce langage, en comparant avec ce que je connais en lisaac et en Java, afin de mettre en perpectives les limites de chacun des langages.
Notez que ce qui s'applique à Lisaac fonctionne avec Ruby, Smalltalk et tous les langages à prototypes.
J'ai beaucoup aimé certains concepts, comme :
Les opérateurs de regexp, le matching et la capture facile
if ($line =~ /(\w+)=(\d+)/ ) {
$ident=$1;
$value=$2;
}
En java, c'est tout un bordel :
Pattern p = Pattern.compile("(\w+)=(\d+)");
Matcher m = p.matcher(line);
boolean b = m.matches();
if(b) {
if (m.groupCount() == 2){
ident = m.group(1);
value = m.group(2);
}
}
Quelle lourdeur !!
La lib regexp Lisaac n'existe pas encore. Il est probable que l'on utilise celle de SmartEiffel, suite au traducteur Eiffel->Lisaac que D. Colnet B. Sonntag ont commencé il y a un an et demi (et que je ne parviens pas à compiler : impossible d'installer correctement smarteiffel...).
Je passerai derrière pour modifier drastiquement l'interface de cette lib que j'intégrerai à STRING, car je pense que qu'une lib Regexp à part (ie dans une classe/prototype distinct) est un concept débile. Les regexp s'appliquent aux chaines et ont donc leur place dans l'objet chaine.
Je l'imagine donc en Lisaac comme suit :
(ident,value) := line.match_and_capture "(\w+)=(\d+)";
Si ça match pas, ident et value valent NULL.
Les tables de hashage builtint
Les tables de hashage sont un outil très puissant et caractéristique de perl.
Je ne vais pas vous la faire en java, il y a n classes différentes pour faire un hash (LinkedHashMap, Hashmap, ...).
En lisaac, c'est à peine mieux, il y en a deux, et ça risque d'augmenter : une histoire de perfs.
J'aime les choses simple et j'aimerai donc qu'il y ait une classe de collection et une classe de hash afin de respecter le concept d'outil générique qui séduit beaucoup de monde dans les langages où ils sont implémentés comme tels.
Des trucs assez énorme en perl sont des écritures du genre :
%hash = ( $chaine =~ m/(\w+)=(\d+)/);
# sans compter :
my %hash = (1,2,4,5);
On pourrait mettre une liste à la place d'ailleurs.
En java, on oublie, la lib est figé, minimal, on est obligé de se faire sa fonction à soi.
Il faut lire ça pour mesurer la débilité de cette lib : http://java.sun.com/javase/6/docs/api/java/util/HashMap.html :
On peut récupérer la liste des clé et des valeurs, via des énumérations, une pauvre interface qui ne permet d'obtenir une sorte de liste chaînée.
Et... Sait-on pourquoi, on peut avoir la liste des valeurs dans une collection.
Bon soyons sérieux, imaginons qu'on ait la détection automatique de path de code en Lisaac (un saint graal très difficile à implémenter qui consiste à demander au compilateur de choisir le parent le plus adapté pour son code. Ca permettra d'avoir un seul proto collection, un seul proto hash, un seul proto set).
En lisaac, comme tout est à faire, on a le droit d'imaginer des choses intelligentes :
- myhash : HASHED_DICTIONARY[STRING,STRING];
myhash := chaine.to_hash "(\w+)=(\d+);";
et tant qu'à faire :
- mylist : ARRAY[STRING];
mylist := chaine.to_list "(\w+)=(\d+);";
Les substitution en regexp
Rien de transcendant, et pour une fois on félicite les auteurs de la lib java qui ont écris un replaceAll intelligent : il gère les captures !!
chaine.replaceAll("(\w+)=([a-r]+)","truc=$1;");
Mais... car il y a un mais, l'opérateur perl est en fait beaucoup plus puissant: comment je fais chaine.replaceAll("=([a-r]+)","truc=$1.uppercase;"); ??
En java, c'est mort (bien évidemment), en Lisaac, on peut encore s'en sortir : au lieu de lui donner une chaine, on lui donne un block de code prenant une liste chaine en argument (les bouts capturés) et renvoyant une chaine.
chaine.replace_all "(\w+)=([a-r]+)" by { nbcap : INTEGER; caps : ARRAY[STRING] ; caps.item i.lowercase +":"+caps.item 2.uppercase; };
Un peu lourd mais efficace.
L'appel de commande bash en quote inverse
C'est typiquement un truc pour unix, mais pour des petits script, c'est vraiment le pied absolu. Pour récupérer le contenu d'une url, ma fénéantise est pleinement assouvie avec un :
my $cont = `curl http://monurl`;
De toutes façons, je ne sais pas coder en shell et j'ai pas l'intention d'apprendre.
La notion de flux facile, avec print MONFLUX ...
La gestion de flux est sympa, car on a qu'à rediriger où on le désir, alors qu'un langage objet implique de créer un objet par flux.
J'ai pas encore assez approfondi ce concept dans perl, mais il y a surement de bonnes idées à prendre.
Les join, grep sur tableaux
On retrouve un peu la notion de map/fold/filter un peu contextualisé. Je considère qu'il y a deux types de langages :
Les langages insuportables où il n'y pas possibilité d'implémenter proprement un map/fold/filter (au hasard, Java...), et les autres.
Les tranches et autres @liste = %h{@t};
L'écriture
@liste = %h{@t};
montre vraiment la puissance de la grammaire de perl. On sent que Larry Wall est linguiste et a voulu aller plus loin.Ca donne des idées. En type ça donne :
HASH(LISTE) => LISTE
quand
HASH(SCALAIRE) => SCALAIRE
Implicitement, ça fait quand même une boucle qui parcours le hash et renvoi une liste de clés !
Ce map implicite sur la liste est très puissant, et ça montre vers où les langages devraient aller (dans le concept) selon moi : revenir à l'analyse du contexte et déterminer ce que le programmeur veut faire. Etre capable de faire des raisonnement de ce genre, mais sur des types beaucoup plus complexe.
Après, il y a des risques...
Ca montre une application intéressante de ce qu'on peut faire si on colle de l'algèbres aux types fondamentaux de nos langages.
Un tableau c'est quoi ? On peut le voir comme le produit de deux ensemble E ∈ |N et F ou tablo[5] est f(5), 5 étant un élément de E, et f(5) un élément de F.
Soit F = Union (i<=n) ui ∈ I et E Union (i<=n) vi ∈ |N
Algébriquement, en posant f bijective (cas idéal, pas de valeur null) ∀ i ∈ I, ∃ j tel que j=f(i)
Or, E est un ensemble, donc une liste d'éléments qu'on peut énumérer avec une fonction G : |N -> E, donc G : |N -> |N
Dans le cas d'un tableau, l'ensemble de départ est toujours un sous ensemble de |N, dans le cas d'une table de hashage, ça peut être n'importe quoi.
Algébriquement f(E) = F, f étant surjective pour toutes les valeurs définies, F étant un ensemble, une liste énumérable, on peut contextuellement faire comprendre au compilateur de quoi il s'agit.
Dans tous les langages que je connais, y compris OCaml, si le message/fonction n'existe pas pour le type, le compilateur répond qu'il ne sait pas quoi faire.
Je n'ai jamais vu le pattern de raisonnement mafonction : ELEMENT1 -> ELEMENT2 => mafonction : COLLECTION[ELEMENT1] : COLLECTION[ELEMENT2].
Sauf en perl... Je sais pas si le cas est traité en dur dans l'analyseur (surement), mais c'est vraiment un concept génial.
C'est ce genre de choses qui font que ce langage a ses fanatiques ;-)
Alors c'est pour ça que je pense à un mécanisme potentiellement dangereux dans pas mal de langages objets : Tout message s'appliquant sur un objet est appelable sur une collection de cet objet.
Par exemple :
ayant
chaine_result := mastring.replace_all "(\w+)=([a-r]+)" by "rien";
on pourra faire
liste_chaine_resultat : ARRAY[STRING];
liste_chaine_resultat := liste_destring.replace_all "(\w+)=([a-r]+)" by "rien";
J'ai pas réfléchi aux côtés noirs de cette idée de map implicite qui casse quand même pas mal le paradigme...
Certaines difficultés m'ont particulièrement énervées en perl, principalement quand ce sont des problèmes inexistant dans d'autres langages. J'ai noté que certaines disparaitront avec Perl 6.
Citons :
La galère dès que l'on veut créer une structure de donnée : pas de notion claire de création de type, il faut créer une table de hashage spécial, il n'y a pas de distinction claire entre type et variable. Ce n'est pas très clair/propre quand on essaye de faire marcher tout cela entre plusieurs fonctions.
On s'en débrouille aisément en les doublant partout où on les utilise, ou en créant un package, mais ces solutions restent lourdes.
- La galère pour passer autre chose que des scalaire en paramètre : on attend perl 6 avec impatience. Personnellement après plusieurs tentatives infructueuses avec les références "comme dans la doc", j'ai laissé tombé et opté pour une très crade variable globale.
- La caractère non typé des variable, voire le point 1 : Ca révèle des surprises, et j'éviterai perl pour du code supérieur à 5000 lignes ou trop complexe, ça deviendrai vite ingérable.
- Les références, c'est puissant, mais c'est un pis allé du à l'absence de notion de type. A l'utilisation c'est pénible, casse-gueule, dangereux, bref tout ce qui m'énerve dans les pointeurs à la C.
Bref, j'aime beaucoup ce langage, même si revenir au procédural est parfois un peu difficile, mais la logique de celui-ci s'y prete bien.
Je pense que je m'en inspirerait grandement lorsque j'aurai enfin ma librairie regexp en Lisaac, afin de pouvoir disposer de toutes les fonctionalités formidables qui y sont offertes, voire peut être plus...
# my 2 cents
Posté par briaeros007 . Évalué à 6.
Mais par rapport à perl :
Je fus "forcé" de me mettre à perl pour la maintenance et l'évolution d'une plateforme web. Et depuis j'ai adopté ce lgg ;)
j'use et j'abuse des tableaux et des hashs, surtout de la facilité à les utiliser, à rajouter un élement, en enlever etc... (bon des fois c'est bien ennuyant entre les references de hash et les scalaire).
Perl n'est pas parfait non plus : manipuler du binaire peut etre assez compliqué (mais bizarrement, pas si compliqué que ça, et puis c'est pas son terrain de jeu initial ;)), mais surtout le parallélisme reste passablement spécial : certaines variables peuvent etre partagé, mais pour partager un tableau de hash ou autre c'est relativement compliqué.
Quant à java, je serais moins dur que toi : ca reste un langage interessant pour apprendre, et surtout, java a une énorme API , et bien moins complexe/mieux documenté a utiliser que certaibs modules de perl (non officiel, qu'il faut rajouter, ...).
Ce que j'aimerais c'est un langage qui allie la facilité du perl, les performances du C, le parallélisme de erlang (pouvoir changer du code à chaud *_*), et la "non gestion" de la mémoire, et aussi adopté un truc simple pour faire des réference et les différencier des données direct.
[^] # Re: my 2 cents
Posté par alice . Évalué à 9.
[^] # Re: my 2 cents
Posté par CrEv (site web personnel) . Évalué à 4.
Java étant assez pauvre, il est facile (mais fastidieux) à lire
Par contre, souvent les programmes en perl vont utiliser beaucoup plus de mot clés (tous les $* par exemple) en plus avec de l'implicite (qui ne pose pas de problème sauf si on en a jamais recontré) et donc forcément c'est plus compliqué si on est pas habitué
mais bon, comme tous les langages faut les apprendre pour les comprendre...
[^] # hors-sujet
Posté par palm123 (site web personnel) . Évalué à 4.
Tu vas aller te promener aux prudhommes bientôt ?
ウィズコロナ
[^] # Re: hors-sujet
Posté par briaeros007 . Évalué à 6.
Et je suis en train de taper une lettre pour les prudhommes pour essayer de changer la dem en licenciement.
Le plus "fun" c'est qu'après que je lui ais dis ses 4 vérités (ah ca fait du bien), et après que la dem soit complètement terminé , il renvoie une lettre en disant "je ne reviendrais pas sur votre demission, mais tout ce que vous dite est faux. Et je n'apporterais aucune justification".
Bref, si avant ça j'hésitais à aller aux prudhommes, maintenant j'hésite plus XD
[^] # Re: hors-sujet
Posté par 2PetitsVerres . Évalué à 10.
Tous les nombres premiers sont impairs, sauf un. Tous les nombres premiers sont impairs, sauf deux.
# t'as tout compris !
Posté par nomorsad . Évalué à 2.
Pour moi, Perl n'est pas juste un énième langage, mais bien une réponse à un besoin : celui de faire plus simplement des taches souvent répétitives, en faisant en sorte d'être cohérent dans la globalité du langage.
Il a su sortir des clivages des langage "typés" ou non "typés" en proposant un typage basé sur la structure, plutôt que sur les données. C'est simple et génial.
Je travaille actuellement sur un projet assez conséquent avec Perl, et tout ce que tu as dit sur la maintenabilité du code est vrai. Par contre, dès que j'ai besoin de structure un peu compliquée, je fait un objet et tout s'éclaire!
Par contre, je ne suis pas fana des Regexp, qui sont, malgré leur puissance, un pustule sur la beauté de la concision du langage.
Cependant, je suis un peu sceptique sur Perl6, car Perl avait la beauté des concepts simple et cohérents. Espèreront que Perl6 ne sera pas yet another usine à gaz...
Perl rend beau. Mangez-en.
[^] # Re: t'as tout compris !
Posté par arthurwolf . Évalué à 2.
J'en pleure à chaque fois.
Vivement noel !
# T'as tout compris
Posté par windu.2b . Évalué à 10.
On s'en débrouille aisément en les doublant partout où on les utilise, ou en créant un package, mais ces solutions restent lourdes.
- La galère pour passer autre chose que des scalaire en paramètre : on attend perl 6 avec impatience. Personnellement après plusieurs tentatives infructueuses avec les références "comme dans la doc", j'ai laissé tombé et opté pour une très crade variable globale.
- La caractère non typé des variable, voire le point 1 : Ca révèle des surprises, et j'éviterai perl pour du code supérieur à 5000 lignes ou trop complexe, ça deviendrai vite ingérable.
- Les références, c'est puissant, mais c'est un pis allé du à l'absence de notion de type. A l'utilisation c'est pénible, casse-gueule, dangereux, bref tout ce qui m'énerve dans les pointeurs à la C.
Ben voilà, tu viens de comprendre pourquoi il existe plusieurs langages : parce que chacun a ses avantages et ses inconvénients.
Tous ces inconvénients n'existent pas en Java (par ex.) !
[^] # Re: T'as tout compris
Posté par windu.2b . Évalué à 10.
if ($line =~ /(\w+)=(\d+)/ ) {
$ident=$1;
$value=$2;
}
Pattern p = Pattern.compile("(\w+)=(\d+)");
Matcher m = p.matcher(line);
boolean b = m.matches();
if(b) {
if (m.groupCount() == 2){
ident = m.group(1);
value = m.group(2);
}
}
Même s'il fait 9 lignes (sans compter les lignes blanches) là où ton exemple en fait 4, je trouve cela bien plus lisible : les noms des classes sont tellement parlants que je sais de suite ce que je suis en train de regarder. Ce n'est pas du tout le cas (du moins pour moi qui ne connais pas Perl) avec ton exemple.
Ensuite, dans l'exemple Java, tu utilises à rallonge la définition des variables alors qu'elles ne semblent pas te resservir plus tard... Autant raccourcir un max (si c'est le nombre de lignes de code qui importe) :
Matcher m = Pattern.compile("(\w+)=(\d+)").matcher(line);
if(m.matches()) {
if (m.groupCount() == 2){
ident = m.group(1);
value = m.group(2);
}
}
C'est plus court (mais perso, je ne trouve pas ça forcément plus lisible)
[^] # Re: T'as tout compris
Posté par CrEv (site web personnel) . Évalué à 4.
ben pas moi, en fait toute l'information est masquée au milieu de définitions et noms de classes qui ne servent pas à grand chose...
En fait toutes ces définitions sont contenues dans =~ mais forcément si on ne le connaît pas on ne comprend pas et on doit "deviner" ce que le programme fait.
Par contre si on apprend cet opérateur ben c'est concis _et_ clair
[^] # Re: T'as tout compris
Posté par Victor STINNER (site web personnel) . Évalué à 7.
import re
m = re.match(r"(\w+)=(\d+)", line)
if m:
__ident = m.group(1)
__value = int(m.group(2))
où __ représente l'indentation, ex: 4 espaces (la base HTML code vire les espaces sur linuxfr).
Je trouve ça plus clair que Perl car où sait d'où viennent et sont les données. Il n'y pas de variable magique comme les $xxx. Perl a l'avantage d'intégrer les expressions régulières à son langage : en Python, il vaut mieux préfixer les chaînes par « r » (chaîne raw, n'interprète pas les antislashs).
[^] # Re: T'as tout compris
Posté par plagiats . Évalué à 1.
(question sincère de débutant à la noix :D)
[^] # Re: T'as tout compris
Posté par Jean B . Évalué à 2.
re.match
renvoie un "matchobject" si il arrive a appliquer le motif sinon None.Il faut donc stocker le résultat et le tester pour éviter d'appeler la méthode "group" sur None.
Par contre si tu n'a qu'un seul résultat et que tu est certaind e l'avoir sans ce cas tu peut faire :
import re
print re.match(r"(\d+).*", line).group(1)
[^] # Re: T'as tout compris
Posté par Victor STINNER (site web personnel) . Évalué à 4.
Oui, j'appelle ça la lisibilité :-) Je n'aime pas le code « malin » (que j'appellerai plutôt « concis » en réalité) qui au final n'est compréhensible que par son auteur. Mais oui, en Python on peut écrire des trucs sales !
ident, value = re.match(r"(\w+)=(\d+)", line).groups()
(cette version stocke value sous forme d'une chaîne de caractères et non pas d'entier)
Note : il existe aussi les groupes nommés :
>>> re.match(r"(?P\w+)=(?P\d+)", "cle=42").groupdict()
{'ident': 'cle', 'value': '42'}
[^] # Re: T'as tout compris
Posté par miRe . Évalué à 4.
my ($ident,$value) = ($line =~ /(\w+)=(\d+)/ );
[^] # Re: T'as tout compris
Posté par miRe . Évalué à 1.
petit exemple de passage d'une table de hashage par référence :
my %hash = (1,"toto",2,"tata");
myfunc(\%hash);
sub myfunc {
my $rhash = shift;
while (my ($key,$value) = each %$rhash){
print "$key = $value\n";
}
}
[^] # Re: T'as tout compris
Posté par Alex . Évalué à 1.
[^] # Re: T'as tout compris
Posté par Ontologia (site web personnel) . Évalué à 2.
Au bout de 2h, j'ai laissé tombé.
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: T'as tout compris
Posté par Octabrain . Évalué à 3.
[^] # Re: T'as tout compris
Posté par matli . Évalué à 2.
Passer des références en paramètres, ça marche sans aucun problème, et heureusement
[^] # Re: T'as tout compris
Posté par totof2000 . Évalué à 2.
d'ailleurs lorsque je fais des choses compliquées avec des références passées à une fonction, je m'arrange pour "déréférencer" le plus vite possible mes variables pour les traiter comme des variables "normales".
[^] # Re: T'as tout compris
Posté par miRe . Évalué à 1.
par contre si tu essayes de passer des array directement à une sub, tu vas certainement avoir quelques problème ...
ps : mon exemple marche parfaitement
# à propos des regexp...
Posté par aedrin . Évalué à 3.
Je t'invite alors à lire ce petit document très instructif sur les regexp : http://swtch.com/~rsc/regexp/regexp1.html qui permet une implémentation très rapide des regexp (sans références arrières) à base d'automates finis.
Je ne sais pas si la lib de SmartEiffel utilise l'implémentation NFA, backtracking ou un mélange des deux... mais ça vaudrait le coup de se renseigner !
my 2 cents
[^] # Re: à propos des regexp...
Posté par Troy McClure (site web personnel) . Évalué à 2.
En gros y'a pas de miracle.
[^] # Commentaire supprimé
Posté par Anonyme . Évalué à 2.
Ce commentaire a été supprimé par l’équipe de modération.
[^] # Re: à propos des regexp...
Posté par Ontologia (site web personnel) . Évalué à 2.
Je crois que je vais implémenter ça, ça sera déjà un début...
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Commentaire supprimé
Posté par Anonyme . Évalué à 2.
Ce commentaire a été supprimé par l’équipe de modération.
[^] # Re: à propos des regexp...
Posté par 태 (site web personnel) . Évalué à 3.
Parce qu'évidemment, pour moi, les expressions rationnelles et les automates finis, c'est tellement la même chose que je ne comprenais pas qu'on puisse faire autrement (et surtout qu'on puisse avoir idée de faire un truc manifestement pire en complexité).
[^] # Re: à propos des regexp...
Posté par Victor STINNER (site web personnel) . Évalué à 2.
# toujours sur les regexps
Posté par Sebastien (site web personnel) . Évalué à 3.
En Python ou Ruby (ou même en Javascript, et sans doute bien d'autres), on peut compiler des regexps et les utiliser avec plus ou moins de lourdeur (pas plus qu'en Java en tout cas), tout en ayant aussi des hashages et listes en types de "base".
(par contre, je n'ai pas compris l'histoire des flux. En Perl comme ailleurs, ce sont des objets derrière, donc je ne vois pas ce qui distinguerait trop STDOUT de System.out)
Bref, j'aime beaucoup ce langage, même si revenir au procédural est parfois un peu difficile,
Rien ne t'empêche de faire autre chose avec Perl, tu sais.
[^] # Re: toujours sur les regexps
Posté par Axioplase ıɥs∀ (site web personnel) . Évalué à 3.
J'utilise d'ailleurs ça dans certains de mes programmes…
Un exemple :
my @regs = ("foo", "b(a)r", "((?:i[^4<_-])|P{2,})\$");
@regs = map qr/$_/, @regs;
my @sent = ("foo", "ia", "bar");
for my $r (@regs) {
for my $s (@sent) {
print "ok $s matched by $r\n" if $s =~ m/$r/;
}
}
print "Done\n";
[^] # Re: toujours sur les regexps
Posté par Sebastien (site web personnel) . Évalué à 1.
[^] # Re: toujours sur les regexps
Posté par Axioplase ıɥs∀ (site web personnel) . Évalué à 2.
D'un autre côté, quand on oublie, un ptit "perldoc perlretut" et zou ! (ou "perldoc " si ton shell est bien), et on te rapelle tout ce que t'as oublié sur le langage…
[^] # Re: toujours sur les regexps
Posté par totof2000 . Évalué à 3.
[^] # Re: toujours sur les regexps
Posté par Victor STINNER (site web personnel) . Évalué à 2.
- m=re.match("regex", "texte")
- x=re.compile("regex"); m=x.match("texte")
# javascript
Posté par CrEv (site web personnel) . Évalué à 0.
Si on prend ton premier exemple de code, ça donnerait :
if(/(\w+)=(\d+)/.test(line)) {
ident = RegExp.$1;
value = RegExp.$2;
}
Autant dire que j'adore le fait d'avoir la regexp entre / / vue comme un objet
Sinon il est vrai que perl c'est bien, mangez-en !
Apprendre perl est assez intéressant, et comme beaucoup une fois qu'on a gouté aux hash à gogo, c'est sympa pour beaucoup de choses.
Mais pour ma part j'ai remplacé tout ce que je faisais en perl pour du ruby. Tous mes scripts annexes tournent en ruby (j'entend par là tout ce qui touche à mes sources, préprocesseurs, rapports, stats, build, etc)
Pour ce qui concerne java, pour en faire de temps en temps, je trouve aussi que c'est un mauvais langage. Ok l'ensemble de lib est intéressant, mais le langage ... beurk.
Il faut toujours écrire beaucoup trop de choses pour avoir un truc sympa, il est trop rigide, et surtout trop pauvre. Les collections sont pas très sympa à manipuler (sauf depuis le 1.6 si je ne me trompe et foreach).
En fait, le langage java est lourd, trop compliqué car inutilement pauvre.
Il parait que ça s'améliore un peu, les annotations sont quand même quelque chose de sympa (même si ça existe ailleurs) mais bon...
impossible de retourner par exemple facilement un liste de valeurs. Si une méthode doit retourner plusieurs valeurs, il faut forcément passer par une structure dédiée (si on veut pas avoir des tableaux partout comme on trouve parfois...)
De même je crois qu'on ne peut pas passer de paramètre modifiable en java...
[^] # Re: javascript
Posté par windu.2b . Évalué à 2.
T'as le droit de créer des listes (et de les faire renvoyer par la méthode), tu sais ?
"De même je crois qu'on ne peut pas passer de paramètre modifiable en java... "
Que veux-tu dire par là ? Que les paramètres reçus par une méthode ne peuvent pas évoluer au sein de la méthode ??? Première nouvelle !
[^] # Re: javascript
Posté par Yusei (Mastodon) . Évalué à 3.
Le résultat sera forcément moins lisible qu'écrire:
a, b, c = ma_methode()
pour récupérer les valeurs.
[^] # Re: javascript
Posté par ckyl . Évalué à 4.
Si ma fonction retourne une liste alors je déclare que ma fonction retourne une liste... Sinon c'est un objet ou un tuple. Maintenant se pose la question quelles sont les objets retournés par ma fonction. De quels types sont-ils ?
Moi plus je sais ce que je manipule, plus c'est agréable à coder même si ca demande plus de lignes "inutiles" dans des exemples triviaux. Dans la vie de tout les jours, 80% du code que je manipule n'a pas été écrit par moi. Je préfère ne pas passer ma vie à essayer de deviner ce que les fonctions que j'appelle sont censées retourner.
Alors quand on parle de Perl, qui ne déclare ni ses arguments si ses types de retour... Ca peut péter (et ca le fera) quand on changera le moindre type d'un argument ou d'un valeur de retour, quand le nombre/ordre des paramètres changera, quand le nombre/ordre des valeurs de retour changera. Vous refactorez jamais ? Vous faites jamais d'erreur dans votre code ? Vous attendez que ça pète à l'exécution pour découvrir que le code est dans un état totalement incohérent ?
Comme toujours c'est marrant sur 100 lignes de code maintenu par une personne.
[^] # Re: javascript
Posté par briaeros007 . Évalué à 1.
Permet moi d'en douter.
J'ai touché à qq lgg objet (perl, java, ...) et le mythe du "tout objet" c'est génial sur le papier, mais à lire tu te dis "mais pourquoi il renvoie une liste ? Qu'est ce qu'il y a dans la liste".
Et ensuite quant tu le lis "mais toto il était à la troisième ou à la quatrième place."
Par contre faire un return ($force,$pression,$durée) , c'est un peu plus lisible que '
list.add(force);
list.add(pression);
list.add(durée);
return list;
(pseudo langage que je vien d'inventer mais qui donne l'idée).
qui ne déclare ni ses arguments si ses types de retour...
/me viens du C où on s'amuse allègrement à changer les types malgré qu'on les a défini avant XD.
(un petit "hack" pas beau, mais utilisé couramment : dans un thread , normalement tu renvoi un pointeur vers une structure contenant les différents arguments pour le threads. Il est courant (mais pas beau), si tu a comme argument juste un entier de faire un cast en long puis en pointeur).
[^] # Re: javascript
Posté par windu.2b . Évalué à 2.
Il existe aussi les types Hashtable, Map, ...
Dans ton exemple, j'utiliserais plutôt des Hashtable que des listes, que chaque case contient une information totalement différente des autres (je ne parle pas forcément d'une différence sur le type).
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 3.
Donc un gars qui veut faire gaffe à l'ordre des arguments retournés utilisera le même chose que java en plus court et comme c'est le cas 9 fois sur 10 il va gagner beaucoup de temps.
Donc le pb n'est pas le langage mais bien le programmeur.
[^] # Re: javascript
Posté par ckyl . Évalué à 2.
Ce qui fait la force des langages de scripting à typage dynamique/failble est que tu peux facilement fourrer tout et n'importe quoi dans ta structure de données. Le langage repousse la responsabilité de faire les choses correctement vers le développeur. Si tu es statiquement et fortement typé tu ne peux et ne veux surtout pas faire ça.
La solution des Pair/Tuple typé via generics est la solution la moins sale si tu veux faire ce genre de choses. Mais certainement pas une hashmap ou toute autre dégueulasserie (encore une fois ce qui est acceptable et plaisant en scripting ne l'est pas pour une appli).
[^] # Re: javascript
Posté par ckyl . Évalué à 2.
Tu viens de découvrir pourquoi on préfère créer un vrai objet. Bravo ! Tu viens de démontrer par toi même à quel point c'est casse gueule :-)
Comme je l'ai dit, si tu veux t'amuser avec les retours multiples, regarde du côté de javatuple. Mais >90% du temps tu veux un vrai objet.
Rappel pour ceux qui ont raté le premier épisode: Java n'est pas un langage de scripting.
[^] # Re: javascript
Posté par briaeros007 . Évalué à 2.
Oui, que cette méthode de passer par une liste X pour renvoyer plusieurs valeurs c'est casse geule, je suis tout a fait d'accord.
(par contre, bcp moins quand c'est prévu par le lgg ;))
Java n'est pas un langage de scripting.
tout a fait d'accord.
[^] # Re: javascript
Posté par allcolor (site web personnel) . Évalué à 2.
public class Plop {
private Pression pression;
private Duree duree;
private Force force;
.....
constructeur(s)
....
setter && getter
}
Et je retourne ça.
Avec eclipse, tu écris les trois params puis generate constructor using fields + generate getters and setters et c'est fait.
[^] # Re: javascript
Posté par briaeros007 . Évalué à 2.
(en réalité en objet, la solution est de travailler en objet pur, cad que les fonctions dépendent d'un objet, et tu met les != résultats intermédiaires nécessaires comme attribut de cet objet (ie pas une fonction "static").)
[^] # Re: javascript
Posté par allcolor (site web personnel) . Évalué à 4.
faire une classe pour _chaque_ fonction qui renvoi plusieurs paramètres... pas lourd du tout.
Tu extrapoles, ce n'est pas ce que j'ai dit... pour moi si tu dois retourner plus qu'un objet, je pense à la base qu'il y a un problème dans ton modèle... mais si tu dois vraiment pour x/y raison, c'est une solution, ça évite le truc dégueux de la liste avec ordre implicite ou de la hashmap fourre-tout non typée... maintenant si tu dois faire ça tout le temps, mon avis est que ton design pue un peu.
[^] # Re: javascript
Posté par Ontologia (site web personnel) . Évalué à 9.
Arguer comme je sais plus ou dans le fil, qu'on peut se planter entre (min,max) et (max,min) est aussi débile que d'affirmer qu'on intervertira jamais min et max quand on les envoie en param de fonction.
Où quand je fais un string2file et que je me plante d'ordre des paramètres chaines...
C'est pas parce que vous connaissez que ça, et que vous n'avez jamais essayé autre chose que c'est forcément mieux que le reste !
Le compilateur est là pour gueuler s'il y a un problème de type, et la signature des fonctions dans la doc et dans eclipse suffit déjà pas mal.
Désolé, mais quand je vois le nombre de contournement interminable et hyper crade que j'observe tous les jours en java à cause de cette limitation, je trouve vraiment cet argument de mauvaise foi.
(J'y tiens car j'ai demandé et obtenu qu'en Lisaac, on puisse rendre plusieurs valeurs. Depuis que j'ai joué avec Caml, je supporte plus les langages rendant qu'une seule valeur(et ceux où on ne peux pas mettre une fonction en param de fonction)...)
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: javascript
Posté par allcolor (site web personnel) . Évalué à 4.
Pour l'exemple de min max, je ferais un inner class qui est juste une structure du genre:
public class MyArray {
__public static class MinMax {
____public int min;
____public int max;
____public MinMax(int min,int max) {
______//
____}
__}
__public MinMax getMinMax() {
____//
____return minMax;
__}
}
Maintenant tout ça ça dépend... de ce que tu veux faire, du design etc
Tout ce que je dis c'est en java, si tu dois ramener plusieurs paramètres, le mieux est de faire comme ça... mais si tu es en java et que tu te retrouves à devoir faire ça tout le temps, ton design est mal pensé, dans tout les cas pour l'implémenter en java.
Je ne dis pas que ça ne sert pas de pouvoir ramener plusieurs paramètres, je dis que ça dépend de ce que tu veux faire, maintenant dans ce que je programme j'ai très rarement ce besoin et si je l'ai je ne ferai certainement jamais le retour d'au choix une liste, tableau d'objet, hashmap parce que ça sapue vraiment.
[^] # Re: javascript
Posté par Ontologia (site web personnel) . Évalué à 3.
Ce langage reprend des concepts vieux de 40 ans (allez voir simula 67) et une syntaxe bas niveau (qui était très bien, très cohérente et très moderne quand C a été conçu). J'eusse aimé que Gossling pusse exaucer son souhait de permettre aux méthodes de renvoyer plusieurs valeurs.
Alors oui, bah avec java, pour faire "propre" on renvoi qu'une valeur, et ça fait des archis crades. De toutes façon, en SSII, enfin la mienne en tout cas, ça passe pas la peer review des gruikitude comme ça. Donc comme je touche pas à java tant que je suis absolument contraint et forcé de l'utiliser....
*Fanboys de java, moinsser moi, faites vous plaisir, c'est de bon coeur ;-)
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 8.
Il nous suffit juste de d'intégrer le fait que tu considères Lisaac comme le summum de l'esthétisme et de la bonne conception et on te pardonne. On en arrive même à ne pas être étonné que tu t'extasies devant du Perl ;-)
[^] # Re: javascript
Posté par Ontologia (site web personnel) . Évalué à 1.
Ya des trucs qui me gonflent dans Lisaac, et qui me manque terriblement...
Par exemple, j'adore Caml, j'en ai pas fait beaucoup, mais j'ai été très impressionné par ce langage.
J'adore par dessus tout le type somme, j'en rêve dans Lisaac, mais c'est difficile à intégrer dans un paradigme objet.
Je trouve que du code fonctionnel est beaucoup plus esthétique : en Lisaac, tu as des horreurs du genre
1.to 5 do { code;};
Le concept de l'itérateur sur le nombre en tant qu'objet est génial, mais ça reste une boucle, et les boucles me donne envie de vomir.
Java est propre, c'est déjà ça de pris, mais d'être bloqué par ce for, de pas pouvoir créer de structure de contrôle, pas de compréhension de liste, pas de fonction en paramètres de fonction, cette syntaxe dépassée (qui était très bien en 1973), désolé, mais je le trouve affreux.
Surtout parce qu'autour de moi tout le monde s'extasie devant ce langage.
Bon, je leur en veux pas, ils connaissent pas grand chose d'autres (php, javascript, les langages mainstream quoi).
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: javascript
Posté par Yusei (Mastodon) . Évalué à 3.
Il y a deux problèmes, le typage et le contenu des valeurs retournées. Pour le typage, rien n'empêche de typer chaque résultat d'une fonction qui en renvoie plusieurs, et dans ce cas je préfère la syntaxe simple que j'ai présentée au dessus.
Pour le contenu des valeurs, il faut bien voir qu'on change la sémantique du résultat de la fonction. Même sur une fonction qui ne renvoie qu'une seule valeur, c'est problématique et ça doit être fait le moins souvent possible. Je ne vois pas vraiment ce que le fait de renvoyer deux ou trois valeurs change au problème. Ta fonction avait un sens, elle en a un nouveau, il faut modifier le code là où elle est utilisée pour refléter le changement. Est-ce vraiment plus dur parce qu'elle renvoit deux valeurs ?
Effectivement, si la seule chose qui change c'est l'ordre dans lequel les valeurs sont renvoyées, le fait de nommer les valeurs (soit en en faisant des attributs d'un objet, soit en les mettant dans une hashtable) résout le problème. Mais concrêtement, est-ce le problème auquel on est confronté dans la vie réelle ? Un codeur ne s'amuse pas à changer l'ordre des valeurs de retour arbitrairement ; quand il change les valeurs de retour, c'est qu'il en change la signification.
Personnellement, étant adepte du Ruby, dans lequel on peut renvoyer plusieurs valeurs, je ne fais ça que pour les cas où c'est adapté. Dès que j'ai besoin d'un objet, je fais un objet. Mais si je fais une fonction qui calcule une équation de droite (ax+b), je renvoie a et b comme valeur de retour, je ne crée pas une classe EquationDeDroite. Et comme je rédige bien sagement mes tests unitaires, ça se passe bien. Mais il faut dire que je travaille surtout tout seul :)
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 2.
non, mais que si tu passes un int en paramètre dans une fonction il n'est pas possible de modifier sa valeur dans la fonction et que cette valeur soit visible en dehors, au retour.
En gros passer des références quoi...
> T'as le droit de créer des listes (et de les faire renvoyer par la méthode), tu sais ?
oué donc je retourne une liste (il faut donc la créer avant de le retourner, ajouter les valeurs, etc) et au retrour je lis ma liste et extrait toutes les valeurs...
myFunc = function() {
return [1, 2];
}
var [a, b] = myFunc();
C'est quand même plus sympa, non ?
[^] # Re: javascript
Posté par Sufflope (site web personnel) . Évalué à 1.
int étant un type de base non-objet (ce qui donne lieu à un autre débat :)) forcément... Utilise Integer.
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 3.
C'est bien le problème de java : un langage objet non objet, avec que des trucs chiant, juste assez bien (surtout niveau plateforme) pour l'utiliser et juste assez chiant pour le détester...
A croire que les concepteurs ont jamais eu les couilles de faire plus qu'un langage "basique" avec rien de nouveau à part virer les pointeurs...
[^] # Re: javascript
Posté par totof2000 . Évalué à 2.
[^] # Re: javascript
Posté par TImaniac (site web personnel) . Évalué à 4.
[^] # Re: javascript
Posté par Sufflope (site web personnel) . Évalué à 1.
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 2.
// Simple regular expression to match http / https / ftp-style URLs.
var parsedURL = /^(\w+)\:\/\/([^\/]+)\/(.*)$/.exec(url);
if (parsedURL) {
var [, protocol, fullhost, fullpath] = parsedURL;
[...]
}
Si ça c'est pas sympa comme code !
[^] # Re: javascript
Posté par thedude . Évalué à 1.
public void maMethode(String url)
{
try
{
URL monURL = new URL(url);
monURL.getProtocol();
monURL.getHost();
monURL.getPath();
URLConnection uc = monURL.openConnection();
// lire ici la reponse du serveur
}
catch(MalformedURLException e)
{
System.out.println("L'url est invalide, veuillez la resaisir");
}
}
[^] # Re: javascript
Posté par yellowiscool . Évalué à 0.
D'ailleurs t'as pas mis la lib à inclure dans ton code.
Envoyé depuis mon lapin.
[^] # Re: javascript
Posté par thedude . Évalué à 3.
Ou alors quand tu met un code snippet en JS, tu precises que le type String est fourni avec le runtime?
Apres, si t'insistes, je peux te mettre le "import java.net.URL", la declaration de la classe, le package, nom de fichier et rajouter les tag @author, param, return etc?
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 3.
je sort un exemple de regexp et tout de suite on sort un cas particulier de java (ou d'un autre langage ça change rien)
Mais si j'avais écrit ça :
var parsed = /^ACTION=(\w+)!IDGEO=(\w+)&USER=(\w+)!([0-9]+)$/.exec(query);
if(parsed) {
var [, action, id, user, userid] = parsed;
[...]
}
comme exemple, ça aurait été moins intéressant...
Et en java tu ferais quoi ?
Une regexp ? (tout de suite c'est lourd)
Des splits comme on voit souvent ? (beurk !!)
[^] # Re: javascript
Posté par windu.2b . Évalué à 1.
En gros passer des références quoi..."
Ah oki...
Bon, int étant un type primitif, sa valeur est passée par copie (il en va de même pour tous les types primitifs dans Java).
Depuis Java 5, il existe l'auto-boxing, qui permet de remplacer un type primitif par son équivalent complexe (Integer pour int) et vice-versa, et cela peut même être implicite (une méthode acceptant un int acceptera aussi un Integer, sans rien avoir à modifier).
Par contre, ces classes englobantes sont immuables.
Du coup, on ne peut pas modifier un Integer, c'est vrai...
"oué donc je retourne une liste (il faut donc la créer avant de le retourner, ajouter les valeurs, etc) et au retrour je lis ma liste et extrait toutes les valeurs...
myFunc = function() {
return [1, 2];
}
var [a, b] = myFunc();
C'est quand même plus sympa, non ? "
La forme est en effet assez lisible et concise... Mais pour un langage objet, je crains qu'elle ne le soit trop !
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 4.
Et pourquoi un langage objet ne devrait pas être concis ??
Il n'y a qu'à prendre ruby : objet et concis.
Pour moi pour le moment un des meilleurs modèle objet que je connaisse (après il y en a ptetre d'autres...)
Pour le reste, ben voilà quoi, je trouve que java est vraiment trop limité côté type "primitifs", et je comprend vraiment pas pourquoi ils ont fait ça vu les limitations que ça provoque...
[^] # Re: javascript
Posté par windu.2b . Évalué à 0.
Le problème dans ce cas serait (selon moi) le suivant :
* Soit on dit que la méthode renvoie un List mais dans ce cas, le compilateur ne sait pas quel type concret utiliser (un des types de l'API officielle Java ? Un type créé par le développeur ? Dans les 2 cas, lequel prendre si plusieurs types concrets existent) ;
* Soit on dit que la méthode renvoie un TypeConcretList mais dans ce cas, on a un code dépendant d'un type concret et non plus d'une interface (List est une interface).
Voilà, je ne dis pas que la solution n'existe pas, mais là comme ça, je ne la vois pas.
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 2.
hop, le problème est réglé, la liste n'est juste qu'une écriture comme une autre pour du retour / affectation de plusieurs valeurs mais pas forcément un type en soit (dans ce cas précis)
Le problème est bien que java est trop fermé pour ces choses et non un problème de langage objet
En ruby par exemple :
def foo
return 1, 2, 3
end
a, b, c = foo()
Il n'y a pas de notation de liste, tableau ou autre, mais le principe est le même (il ne faut pas du tout se focaliser sur la notation en javascript)
[^] # Re: javascript
Posté par windu.2b . Évalué à 2.
public TypeA, TypeB, TypeC maMethode()
{
[...] // On déclare et on utilise les variables a, b et c
return a, b, c;
}
// Utilisation de la méthode avec triple-renvoi
a1, b1, c1 = maMethode();
Faut voir... Là comme ça, je vois surtout le travail qu'il y aurait à faire au niveau du compilo (parce qu'un tel truc n'a jamais été envisagé).
Par contre, ton exemple en ruby me fait peur ! Comment savoir combien et de quels types seront les paramètres de retour d'une méthode ?
[^] # Re: javascript
Posté par ckyl . Évalué à 3.
There are a bunch of things that I'd do differently. There are a number of things that I'm not entirely happy with and it's not clear what the right answer is. I'm not really happy with the schism between interfaces and classes; in many ways it feels like the right solution wouldn't get in the way.
There have been a number of things -- like, for example, multiple return values -- that these days I kind of wish I had added. That was one where I really liked the feature and most other people just sort of went, "Huh?"
Il y a d'ailleurs eu quelques RFE n'ont pas eu de suite puisqu'il faudrait péter la compatibilité de la VM pour le supporter. Normalement pour le langage ca peut rester compatible (de mémoire).
Si tu veux jouer avec ca, regarde du côté de javatuple: http://javatuple.com/index.shtml
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 2.
Pour ce qui est du ruby, pour ma part avec des langages de ce genre et des fonctions idem ... ben c'est documenté en codant est la doc est mise à jour (javadoc and co) Ca reste un moyen correct même si pas parfait...
[^] # Re: javascript
Posté par thedude . Évalué à 2.
Les collections etaient effectivement particulierement pete couille jusqu'a java5 et l'apparition des generics.
Le pb est que l'implem des generics est mauvaise (tu te tapes vite la tete contre les murs quand tu pousses un peu l'utilisation) et for each est foireux, car pas possible de modifier la collection "foreachee": ca cree un Iterator behind the scenes, et malheureusement, tu n'a pas acces a cet iterator, donc modif = ConcurrentModificationException dans la face.
Sur ce point la, tu as tout a fait raison.
Le probleme la est que Sun a les petoches de casser quoi que ce soit niveau compat avec java1.4/5 et anterieurs, et qu'on se traine donc des boulets.
A mon humble avis, faudrait qu'ils prennent leurs couilles a deux mains, cassent la compat' en disant "desole pour les familles, tout ca, mais merci pour tout l'poisson, hein", nous mettent des vrais generics, des vrais getter et setter (ie des properties, pas des methodes, cf ActionScript) et autres choses sympatoches.
Il parait que ça s'améliore un peu, les annotations sont quand même quelque chose de sympa (même si ça existe ailleurs) mais bon...
C'est pas qq chose de sympa, c'est juste de la balle. Les annotations spring et hibernate me rendent la vie infiniment plus facile au quotidien
impossible de retourner par exemple facilement un liste de valeurs.Si une méthode doit retourner plusieurs valeurs, il faut forcément passer par une structure dédiée (si on veut pas avoir des tableaux partout comme on trouve parfois...)
Alors la par contre...
Ce que tu veux faire est une grouikerie sans nom. Je trouve ca dans le code au boulot (ie une List non typee avec ungros bordel dedans), c'est 10 coups de trique en publique pour le cochon qui a commite ca).
Non, une methode retourne un et un seul objet. Ou rien du tout.
Non, elle ne modifie pas un tableau passe en entree comme ca se fait en C.
Ce genre de choses sont simplement degueulasses, c'est gerable en langage de script parce que tu vas avoir qq centaines de lignes ecrites par la meme personne, ca se fait en C parce qu'on peut pas trop faire autrement, mais dans un langage objet haut niveau, c'est a proscrire.
Une methode retourne un objet. Si elle doit retourner plusieurs choses qui ne sont pas liee (ie, qui ne sont pas membres d'un meme objet), c'est que ton design est a chier, ta methode fait beacuoup trop et tu DOIS la splitter en plusieurs autres methodes. et si tu vois pas l'interet de le faire, soit tu n'utilises pas le bon langage, soit t'es trop con. Je vote plutot pour la reponse 1, mais la 2 se voit quand meme de temps a autres.
Alors, ouais, ca implique plus de code, mais au moins ca te met des gardes fous, ton code ne va pas peter parce que jean guy a patcher la fonction et a change l'ordre des parametres.
[^] # Re: javascript
Posté par Jean B . Évalué à 3.
Pourquoi multiples valeurs de retours voudrais dire pas de contrôles des types ?
Il est vrai que je ne connais pas de langage implémentant les deux concepts, mais rien n'empêche de le faire:
public final (int, String) foobar(String foo) {
// snip
}
[^] # Re: javascript
Posté par thedude . Évalué à 0.
Un n-uplet est plus ou moins un type, mais ca ne resoud pas le pb conceptuel de la grouikerie: soit tu retournes un ensemble coherent de valeurs, et dans ce cas tu as un objet pour les encapsuler, probleme resolu, soit tu retourne des trucs qui n'ont rien a voir, et tu veux faire une immondice.
Je comprends tout a fait que cette immondice est parfaitement gerable et acceptable dans certain cas (je pense notamment a des petits code, genre scripts ou autres, ya surement d'autres trucs auquels j'ai pas pense), mais ca n'a clairement pas sa place dans un langage comme java.
[^] # Re: javascript
Posté par beagf (site web personnel) . Évalué à 6.
Mais Java gère les séries de paramètres typées ainsi qu'un valeur de retour typée, qu'est-ce qui empêche de gérer une série de valeur de retour typées ?
Je ne vois pas ce qu'il y a de degeulasse dans les valeurs de retour multiples, bien au contraire, ça évite la création de miriades de petits objets qui ne servent à rien d'autre.
Par contre, il faut bien sûr le faire correctement, c'est-à-dire typé.
Si tu est contre les valeurs de retour mutltiple, comment fais-tu pour tolérer les paramètre multiple ? Pourquoi ne pas passer tous les paramètres dans l'objet ?
[^] # Re: javascript
Posté par Sytoka Modon (site web personnel) . Évalué à 1.
D'ailleurs, c'est marrant, dès qu'on parle Lissac ici, je sors mon Sather;-)
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 2.
Pour la deuxième partie je suis moins d'accord.
Le "problème" est qu'on nous a toujours appris qu'une fonction doit retourner 0 ou 1 objet. Mais pourquoi donc ? Est-ce vraiment si obligatoire ? Ne peut on pas réfléchir un peu et faire autrement, aller plus loin ?
Imaginons que dans un programme on ait un tableau de valeurs numériques. On veut à un moment donné obtenir les bornes (ie min et max du tableau)
On peut évidemment parcourir 2 fois le tableau et renvoyer une fois le min, une fois le max.... mais si ces valeurs sont faites pour être utilisées en même temps, c'est un peu idiot.
Pourquoi ne pas avoir une fonction "getMinMax" qui nous retournerais le min _et_ le max du tableau ?
C'est pas hyper tordu, c'est logique mais c'est interdit pour quelle raison ? parce qu'on peu _aussi_ écrire de la daube avec ? Pour moi c'est pas une raison on peut écrire de la merde avec n'importe quel langage...
Et dans le cas min/max créer un objet pour ses valeurs serait complètement idiot, inutile à mon avis.
(et sinon les langages de script c'est pas que pour les petits programmes à la con de quelques lignes, pour le moment je bosse surtout avec un langage interprété, à prototype et il fait un peu moins de 60 000 lignes sans les libs...)
[^] # Re: javascript
Posté par thedude . Évalué à 3.
Dans un langage objet par contre, par essence, tu vas passer par des classes pour ce genre d'operations (ie, tu ne vas pas utiliser une "fonction" mais une methode d'une classe).
Deja en java, utiliser un tableau, c'est pas courant. Tu vas utiliser une List ou un Set suivant le besoin. List et Set qui sont des classes et peuvent donc avoir des methodes, a tout hasard getMin et getMax.
Tu peux creer une classe ManipulateurDeList qui prend une list ou tableau en input ou quoi que ce soit d'autre.
La philosophie voudrait meme que tu utilises l'interface Comparable pour pouvoir appliquer getMin et getMax a autre chose que des valeurs numeriques. Ca prend une autre dimension, c'est plus complique, mais ca tombe bien, c'est utilise pour faire des choses complique, pas pour faire des choses simple vite fait.
Si tu as *besoin* de retourner 2 objets, c'est que ta structure d'objet et/ou ton api sont mauvaises.
Disons que tu vas pas creer une classe rien que pour ca en codant ta methode, tu vas te poser et reflechir avant meme de faire la classe en question et reflechir a son API. Si ca arrive, tu es totalement passe a cote des fondements des langages pur objets.
Oui, c'est chiant, et c'est pour ca que l'objet pur est lourd a utiliser, faut avoir une bonne raison de faire de l'objet pur.
Je veux bien croire qu'il ya qq cas specifique limites, mais ca ne justifie pas de faire rentrer une immondice pareille dans le langage.
Je sais pas si tu maitrises bien les langages objets ou pas (aucune animosite ni condescendance), mais j'ai comme l'impression que tu abordes les langages objet avec une philosphie imperatif: forcement ca va pas passer (je te rassure, je ferais tres certainement pareil dans l'autre sens).
Le probleme que je vois avec les retours multiples, c'est que si tu retournes un n-uplet (int, int, int), tu n'as pas la moindre idee de ce qu'est chaque parametre.
C'est une grouikerie parce que ca te permet de coder au kilometre sans meme penser aux implications de ton code ,comment il va etre utilise ou comment il va etre maintenu.
Avec un objet, tu vas faire un getMin() et t'es sur de pas te planter.
Avec une structure tu vas faire un retour.min, et pareil, sur de pas te planter.
Avec un n uplet tu fais un retour.get(0) sans plus d'infos, c'est du code qui ne demande qu'a te peter a la gueule. Jean Rene va passer par la, modifier le code, ca va te retourner (max, min) au lieu de (min, max) parce qu'il a patche a 4h00 du matin, et tu va mettre 2 jours a trouver le bug.
Pendant ec temps la, moi je bosse^W troll sur LFR.
A la rigueur, faire des trucs comme en actionscript/javascript: retourner un objet dynamique (ie avec des membres cree a la volee), ca parait un compromis raisonnable. Mais conceptuellemet, c'est pareil, t'as juste une souplesse a l'utilisation de creer ta classe dynamiquement.
Sinon, pour les liste de parametres, j'ai du mal a voir l'interet, peut etre que je suis trop idiot ou ferme. Toujours est il que je trouve ca tres crade aussi.
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 3.
Si j'ai des données qui sont un tableau d'entier (juste un tableau, pas autre chose, pas de liste, pas de hash, etc) ça fout un bordél énorme juste pour un min max...
Et ça ne corrige toujours pas le fait que getMin va parcourir mon tableau et getMax aussi alors que c'est totalement idiot
Et le coup du max,min qui devient min,max...
Quel est la différence entre la déclaration de valeur(s) de retour et la déclaration des paramètres ?
Et en l'occurence j'aurais tendance à penser que getMinMax retourne min, max et getMaxMin retourne max, min
> une immondice pareille dans le langage
> tres crade
Etrange, c'est justement ce que pense beaucoup de programmeurs java...
Pour l'histoire de langage objet, etc c'était surtout pour présenter un exemple simple. D'ailleurs mon getMinMax est par exemple une méthode de classe.
Mais dans un programme ou, sur mon tableau, jamais je n'utiliserai min sans max (voyons ça comme des limites) pourquoi je devrais utiliser deux méthodes différentes ?
C'est là qu'on a un comportement illogique et consommateur de resources.
Ou alors je sais pas, je fais un myArray.calculateMinMax() suivit de myArray.getMin() et myArray.getMax() ? Là ça pue !
Pour ce qui est de faire de l'objet pur, etc, voir le modèle objet de ruby, il est assez bien foutu, va beaucoup plus loin que celui de java entre autre.
[^] # Re: javascript
Posté par thedude . Évalué à 4.
Possible, j'en suis un apres tout :)
Et ça ne corrige toujours pas le fait que getMin va parcourir mon tableau et getMax aussi alors que c'est totalement idiot
Probleme d'implementation, getMin et getMax peuvent faire appel a private computeBounds().
C'est l'interet de l'objet : pouvoir encapsuler tout ca.
Si le min est toujours utilise avec le max, tu calcule les 2 en meme temps, sinon tu les separes.
Quel est la différence entre la déclaration de valeur(s) de retour et la déclaration des paramètres ?
La difference, c'est que tu recuperes 2 entiers, pas un min et un max. Tu ne peux pas differencier les deux sans lire la doc ou le code de la fonction.
Et en l'occurence j'aurais tendance à penser que getMinMax retourne min, max et getMaxMin retourne max, min
Ou pas.
Sur ce cas tres particulier, c'est effectivement dur de penser le contraire. Mais tu te reposes sur une convention, et ca rend ton code plus sujet a gros bug.
Et si tu rajoute la moyenne et l'ecart type, tu fais quoi? getMinMaxAverageEcartType? sympa ta fonction dis donc.
jamais je n'utiliserai min sans max (voyons ça comme des limites)
Ce sont des limites qui sont lies l'une a l'autre?
Ca n'est pas donc pas un n-uplet, mais une limite, qui est un objet avec une semantique et des metodes particuliere: ca justifie clairement une classe.
Cree alors une classe Bounds retourne la: tu auras un modele plus robuste et evolutif.
Tu n'as pas besoin de modele robuste et ca t'emboucanne tout ca?
Java ne repond donc pas a ta problematique, tout simplement.
[^] # Re: javascript
Posté par MsieurHappy . Évalué à 2.
Du coup, on ne devrait pas avoir de méthode avec de multiples arguments parce que l'on ne peut pas les différencier sans regarder la doc ?
Non mais n'importe quoi.
Quand je vois les solutions proposée pour résoudre un simple retour de (min, max), je ne suis pas étonné que les programmes Java soit aussi lourd.
Je suis toujours surpris de voir à quel point Java "rigidifie" l'esprit des codeurs. En fait, avec Java, on perd énormément d'expressivité, parce qu'il ne faudrait surtout pas laisser une partie de la responsabilité de la qualité du code aux devs. Et le pire, toutes ces contraintes n'empêchent pas de pondre du code immonde. Autant utiliser autre chose si on a le choix.
[^] # Re: javascript
Posté par hocwp (site web personnel) . Évalué à 2.
Par exemple en lisp ça donnerai quelque chose comme ça :
(ma-fonction (...)
...
(values :min -10 :max 20))
(values-bind (:min min :max max) (ma-fonction)
... utilisation de min et max ...)
ou :
(values-bind (:max max :min min) (ma-fonction)
... utilisation de min et max ...)
Il n'y a plus besoin de savoir dans quel ordre ma-fonction retourne les valeurs min et max puisque ces valeurs sont nommées. La fonction values-bind n'existe pas dans le standard mais elle est très facile à coder.
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 2.
Tu peux adopter avec Java aussi cette solution de facilité même si ce n'est pas supporté par la syntaxe du langage, tout les retours de paramètres multiples ne sont rien d'autre que des tuples en Python
Juste qu'on t'explique que dans le monde objet on préférera utiliser un vrai type de données, une classe en guise de retour qui supporte le contrat et rien que le contrat. On garantit l'encapsulation dès le départ.
Si tes besoins évoluent par la suite,
genre je rajoute, un troisième champ eh ben c'est vrai avec un Hashmap .... l'ancien code appelant marche toujours.
Maintenant je veux pouvoir pouvoir rajouter des comportement à ce résultat comme par exemple le rendre sérialisable. .... et puis on s'aperçoit que finalement la table de hachage c'est pas si bien que ca parce que ca rame parce qu'il manque des trucs ou simplement parce tien un nouveau type qui fait tout ca existe dans le langage
Les sets python sont bien utiles mais n'existaient pas dasn les premières versions
http://docs.python.org/library/sets.html
soit on surcharge alors les Hash qui devient un vrai type.
Avec Python tu vas commencer a surcharger les built'in types, ...
Mais dès le départ tu as fait un choix sur la structure de donnée , peu importe que cette structure fasse partie intégrante du langage ou non.
Or mon contrat disait que je voulais getMin, GetMax,GetMinMax et pas getKeys, get Values, getDict...
Manque de bol, partout dans mon code appelant je les ai utilisés et maintenant que j'ai choisi d'utiliser des Sets, je suis marron.
En plus ma lib a été diffusée et j'oblige également tous mes clients à s'aligner.
Je suis d'accord, est-ce que le jeu en vaut la chandelle , tout est affaire de compromis entre résultat à court terme et évolutivité.
Je suis d'accord que, qui peut le plus peut le moins et qu'un langage plus souple n'empêche pas la rigueur.
Mais il ne faut pas sacrifier les bonnes pratiques.
[^] # Re: javascript
Posté par windu.2b . Évalué à 2.
Dans ce cas, n'aurait-il pas mieux valu (en Java en tout cas) créer un type qui contient la hashtable, plutôt qu'un type qui l'étend ?
Parce que l'héritage, c'est bien beau mais ça peut vite coincer (entre autre, parce qu'on ne peut pas faire de l'héritage multiple et que l'on a peut-être déjà étendu une autre classe).
Selon moi, un tuple contient un type particulier (la hashtable) pour gérer sa tambouille interne, mais n'est pas ce type.
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 2.
[^] # Re: javascript
Posté par allcolor (site web personnel) . Évalué à 3.
Ou alors je sais pas, je fais un myArray.calculateMinMax() suivit de myArray.getMin() et myArray.getMax() ? Là ça pue !
Non tu fais simplement un truc qui calcule ton minmax une fois au moment du getMin ou getMax et l'appelle à l'autre ramène la valeur calculée précédemment, si l'état interne du tableau change (donc que tu dois recalculer min ou max) tu mets le boolean et à un appel de getMin ou getMax tu refais le calcul en sauvant dans l'état interne de l'objet le min et le max.
int min;
int max;
int minMaxValid = false;
private void recalculMinMax() {
__if (!minMaxValid) {
____...
____minMaxValid = true;
__}
}
public void getMin() {
__recalculMinMax();
__return min;
}
public void getMax() {
__recalculMinMax();
__return max;
}
public void changeUnTrucDuTableau() {
__// ...
__minMaxValid = false;
}
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 3.
Non mais sérieux, c'est pas quelque chose de simple ton truc.
C'est inutilement compliqué ça
Surtout que cette solution oblige aussi à redéfinir _toutes_ les méthodes d'accès (en écriture, push, etc) du tableau.
Imaginons que je veuille rajouter mon getMinMax à une classe de tableau. Je vais faire une nouvelle classe héritant de mon tableau.
Avec ma solution je défini _une_ méthode qui fait ce que je veux -> le code est clair, très compréhensible, concis mais pas inutilement, très facile à maintenir.
Si j'utilise cette solution je commence par définir _trois_ méthodes (recalculMinMax, getMin, getMax) et je surcharge _toutes_ les autres méthodes modifiant l'objet pour changer mon booléen de modification.
Le code est lourd, complexe, chiant, inutilement long, plus compliqué à maintenir.
Et si j'ajoute une fonctionnalité dans ma classe mère :
- avec ma solution celle ci est dispo tout de suite dans ma classe fille, sans modifier une ligne de code
- avec la solution "java" ... ça dépend. Si cette méthode est une méthode d'accès, alors ça roule. Si par contre c'est une méthode de modification ... ben soit je l'utilise telle quelle et mon getMin / getMax est foutu, soit il faut que je la resurcharge dans ma classe fille.
Ca devient très vite le bordel et on est justement dans un cas où le système se casse la gueule en maintenance, car une autre personne que celle qui a écrit le premier code va rajouter la fonctionnalité dans la classe mère et ne comprendra jamais pourquoi son getMin / getMax est devenu tout pourri et ne renvoi pas les bonnes valeurs.
ps : pour tous ceux qui veulent include du code dans un commentaire :
s/ / /g et ça roule !
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 4.
s/ / /g
[^] # Re: javascript
Posté par Alex . Évalué à 1.
[^] # Re: javascript
Posté par windu.2b . Évalué à 2.
Sa solution fonctionne : elle repose juste sur un booléen en interne qui permet de ne pas refaire un traitement pouvant être long (rechercher le min et le max d'un tableau, ...) inutilement. Je ne vois pas ce qu'elle a de complexe/débile/whatever
[^] # Re: javascript
Posté par beagf (site web personnel) . Évalué à 4.
Cette solution impose de surcharger toutes les méthode qui modifient le tableau, ce qui veut dire :
- ralentir toutes les modifications du tableau, un appel surchargé à un coût non-néglgeable quand il est fait régulièrement ce qui est souvent le cas pour les modifications de tableaux ;
- rendre la maintenance très complexe, la personne qui maintien le code du tableau n'est pas forcément au courrant de toutes les classes dérivées.
Tout ça juste pour une solution soit-disant "propre" alors que les valeurs de retour multiple serait bien plus simples et beaucoup moins complexes à gérer et maintenir.
Avec les retours multiple on a une fonction d'une vingtaine de lignes pour laquelle une entrée dans la doc est suffisante et dont la maintenance est simple.
Avec la solution java, on a une base d'un quarantaine de lignes plus quatre ou cinq lignes par fonctions d'acces. La doc deviens beaucoup moins simple et la maintenance est galère car le dev doit surveiller toutes les modif de la classe de base et vérifier qu'il n'y a pas de nouvelles fonctions d'accès à surcharger.
On perd la transparence de l'aspect objet, la fonction minmax deviens bien plus dépendante de l'api exposée par la classe de base.
De plus, au départ la fonction minmax éxiste pour éviter de faire deux fois le coûteux parcours du tableau, mais vu que tous les acces deviennent plus coûteux le gain final est négatif.
Bref, mauvaise solution.
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 4.
http://linuxfr.org/comments/1000473.html#1000473 sous-entend qu'il ne va pas reparcourir le tableau en dynamique à chaque fois qu'il appelle getMinMax.
En java tu peux créer une classe interne MinMax adapté
comme ici
http://linuxfr.org/comments/1000492.html#1000492
C'est peut -être plus lourd mais par la suite tu voudra aussi l'écart type, la variance et ta belle solution de multi-liste t'obligera à un moment à tout refactoriser ton code appelant.
Par la suite on peut se créer une vraie classe qui supporte ce contrat sans tout péter.
L'autre solution est que ta classe supporte ce contrat via un interface.
Si j'ai défini le bon interface avec getMin, getMax ou une classe dédié peu importe que par la suite je mette en cache ou non un booléen, que je place un Observer puisque c'est encapsulé.
En plus il n'y a pas de surcharge de toutes les méthodes comme la solution proposée plus haut ici.
Toi avec tes 2 variables en sortie non typée faudra que tu pètes tout le code appelant ou que tu gardes getMinMax par rétrocompatibilité ad vitam eternam mais c'est vrai que quand on est à la bourre c'est plus rapide d'aller au plus simple.
Bref tout ca se discute.
Java permet moins de faire de conneries au prix d'une certaine lourdeur.
Les langages ala pyhton &co permettent plus de souplesse mais parfois au détriment de l'évolutivité.
Là où c'est paradoxal , c'est que c'est justement des langages qui devraient être réservés à des programmeurs expérimentés qui séduisent aussi les néophytes.
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 2.
ra mais c'est pas vrai, vous le faites exprès ?
Un retour de fonction en java est bien typé, non ?
Donc si on permet d'avoir plusieurs valeurs de retour, pourquoi ça deviendrait non typé par magie ?
Pourquoi ne pas imaginer :
public int min, int max getMinMax()
?
Et après, franchement pour sortir un min et un max en même temps s'il faut sortir une sous classe, une interface spécifique, coller un observer, etc ... ben en fait je comprend de plus en plus le journal de Ploum... http://linuxfr.org/~ploum/27723.html
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 2.
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 2.
http://fr.wikipedia.org/wiki/Type_abstrait
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 0.
c'est bon là ?
non mais c'est bien rigolo votre truc, mais si tu écris une fonction getMax qui s'appuie sur un tableau tu va créer un type pour ça ou retourner un entier (si je n'ai qu'un tableau d'entier) ?
M'enfin, tout ça pour ce qui est à la base un exemple, juste des contraintes prises comme ça pour expliquer que ça peut servir, mais ça fout tellement les boules aux codeurs java que ça en devient ridicule.
- Bonjour je voudrais calculer simultanément et retourner le min et le max d'un tableau d'entier.
- Ok, tu fais une classe interne, un observer, deux ou trois ko de code et ça roule. autre chose ?
A oui, on pourrait faire plus simple mais tu vois c'est pas drole, on se ferai chier, c'est pas bien, c'est une erreur, c'est toi qui sait pas, c'est pas propre, c'est trop compliqué pour un neuneu (rayer les mentions inutiles)
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 1.
typedef int min;
c'est bon là ?
Non mais c'est pas grave, fais toi plaisir
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 2.
> Ca on le sait mais 2 int ca ne fait pas un type abstrait de données
Mais je ne veux pas un type abstrait, je veux que ma fonction retourne plusieurs valeurs.
Mais bon, faut croire que c'est si sympa de créer tout un bordel pour ça...
[^] # Re: javascript
Posté par thedude . Évalué à 0.
Bon courage dans 2 ans pour rajouter la moyenne et l'ecart type sans tout peter.
On te l'a indique plus haut, t'as plusieurs choix, casser l'api en refactorer le nom de la fonction (mais c'est tes clients qui vont gueuler) ou casser la coherence de ton api en rajoutant getMoyenneEcartType (c'est tes clients qui vont gueuler aussi la) ou le pire du pire, rajouter les valeurs a getMinMax sans toucher au nom (m'est avis que ca va gueuler aussi).
Bref, tout est question de compromis, ca peut etre gerable de faire ce que tu veux, maintenant faut voire que java est enormement utilise en entreprise, que le code metier en entreprise est appele a evolue en permanence, que la compatibilite avec l'existant est generalement critique, donc on peut pas se permettre ce genre de grouikerie.
Quand a l'appel surcharge a add() sur la collection, je me gausse, on parle de setter un booleen la, une ligne de code, une petite affectation toute simple, si t'es rendu a ce niveau d'optimisation, elle est belle ta vie. Avec un peu de chance, le JIT va meme se rendre compte que l'affectation peut etre zappee dans 99% des cas et tu verras rien.
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 1.
faut voir, j'ai plutôt tendancer à penser qu'un code simple _immédiatement_ est justement plus facile à faire évoluer car il est beaucoup moins complexe à comprendre et moins source de problème.
Mais combien de programmes sont inutilement compliqués derrière des "mais si dans x années qqn code un truc non voulu, non prévu et si il le fait pas exactement comme il faut, ne respecte pas les conventions, etc" ?
C'est bien de vouloir prévoir les cas, mais combien ne se produiront _jamais_ alors que ça aura complexifié le code ?
sinon, pour le getMinMax ecart type toussa, j'ai pas vu la solution (pourtant si chère aux programmeurs java) je prend eclipse refactor toussa et hop rulez ! le fait que j'ai utilisé ailleurs ou non mon minmax est automatiquemnt trouvé / modifié / etc
> Quand a l'appel surcharge a add() sur la collection, je me gausse, on parle de setter un booleen la, une ligne de code, une petite affectation toute simple, si t'es rendu a ce niveau d'optimisation, elle est belle ta vie
Là je pense que t'as pas du saisir ce que je disais. Je n'ai rien contre le fait de rajouter un booléen mais contre le fait de devoir surcharger _toutes_ les méthodes de modification de ma classe.
Si je rajoute une méthode de modification dans ma classe mère alors il _faut_ que je la surcharge dans ma classe fille.
Et toi qui parle de maintenance / évolutivité à qq années, c'est bien pire que de savoir comment je pourrai un jour rajouté un écart type
C'est typiquement le genre de chose qui sera oublié et là l'intégralité des résultats de mon getMinMax sera faux et pour comprendre d'où ça vient rapidement...
[^] # Re: javascript
Posté par briaeros007 . Évalué à 3.
Et parfois ce genre de contraintes est mise sur le cahier des charges.
[^] # Re: javascript
Posté par allcolor (site web personnel) . Évalué à 3.
Là je pense que t'as pas du saisir ce que je disais. Je n'ai rien contre le fait de rajouter un booléen mais contre le fait de devoir surcharger _toutes_ les méthodes de modification de ma classe.
Si je rajoute une méthode de modification dans ma classe mère alors il _faut_ que je la surcharge dans ma classe fille.
Non c'est faux... si on ne peux accéder à l'état interne de la classe mère que par les méthodes (public ou protected) auquels elle donne accès (et que dans toutes ces méthode la classe mère, le booléen est setté correctement), tu n'as pas à faire ça... car si dans ta classe enfant tu modifies l'état interne de la classe mère tu es forcément passer par une méthode de la classe mère qui elle gère ce booléen, maintenant si tu laisses la classe enfant directement dépatouiller l'état interne de la classe mère (des fields en protected ou package private) alors là oui, elle (la classe fille) devra se soucier du flag... mais ça c'est de la mauvaise encapsulation, ta classe enfant ne devrait pas pouvoir le faire sans passer par des méthodes de la classe mère qui gère le flag, donc quand c'est bien fait, le truc que tu racontes est simplement et purement faux.
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 2.
Non c'est vrai !
> la classe mère qui gère le flag
non, c'est la classe fille !
> quand c'est bien fait, le truc que tu racontes est simplement et purement faux
ben non, si c'était bien fait on aurait pas à faire toutes ces conneries de java
Allez on reprend pour ceux du fond qui ne suivent pas.
disclaimer : ceci est un exemple, pour comprendre, qu'on me sorte pas des conneries de collection ou autre c'est pour expliquer un principe, une logique, non pour écrire un exemple réel (j'suis pas sur que tout le monde ait compris ça déjà...)
Imaginons une classe de tableau : (ha oui, j'écris ni en ruby, ni en java, ni en js, etc c'est juste pour comprendre sans s'en soucier, et oui j'ai pas mis de test, de validation, etc on s'en branle)
class Array
def get index
return data_au_bon_index
end
def set index, value
data_au_bon_index = value
end
end
Maintenant j'ai deux classes utilisant ceci, en rajoutant des besoins spécifiques et non nécessaires à tous (oui les noms sont pourris je m'en fou aussi c'est un exemple) :
class ArrayWithExtraFunctionnality1 < Array
def plop
[...]
end
end
class ArrayWithMinMax <Array
def getMinMax
end
end
Version sympa :
class ArrayWithMinMax < Array
def getMinMax
[...]
return min, max
end
end
Version "java"
class ArrayWithMinMax < Array
boolean internalStateModified = false
def getMin
if internalStateModified
computeMinMax
end
return min
end
def getMax
if internalStateModified
computeMinMax
end
return max
end
def set index, value
internalStateModified = true
super.set(index, value)
end
end
Maintenant je veux rajouter la méthode concat dans ma classe mère car je sais qu'elle sera utilisée par _toutes_ les classes filles :
class Array
[...]
def concat otherArray
[...]
end
end
Avec la solution simple ... ben je change rien, je peux l'utiliser
Avec la solution "java" :
class ArrayWithMinMax < Array
[...]
def concat otherArray
internalStateModified = true
super.concat otherArray
end
end
Il faut donc que je maintienne ma classe fille quand je rajoute des choses dans la classe mère.
Ha oui, je veux pas que mon "internalStateModified" soit dans la classe mère, je veux juste rajouter un getMinMax qui est utile que pour ce cas précis.
En gros, comment proposer une architecture complexe juste pour rajouter le calcul et le retour de deux valeurs simultanément...
[^] # Re: javascript
Posté par allcolor (site web personnel) . Évalué à 2.
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 3.
Si la classe mère est celle contenant le minmax, c'est quoi ma classe fille ?
Evidemment si je colle minmax dans ma classe mère alors la classe fille est simple, mais ça ne correspond plus du tout à l'exemple dont je parle _depuis le début_
question subsidiaire : pourquoi ne pas faire, juste un peu, abstraction de minmax etc pour juste tenter de comprendre l'exemple ?
Je demande pas comment me passer d'un minmax, comment optimiser ce cas hyper précis puisque c'est un _exemple_
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 2.
On a une classe List de base.
On décide de la sous-classer BoundedList avec cette fameuse méthode getMinMax.
Pour l'optimiser on rajoute ce fameux booléen et min et max dans la sous-classe.Je n'accède pas à l'état de la classe mère, je l'étend en lui rajoutant des champs .. privés bien entendu
Pour chaque méthode de modification de la classe mère List, je suis bien obligé de surcharger la méthode dans la classe fille en appelant la méthode mère et en repositionnant mon booléen à faux.
Si le contrat de List s'enrichit avec une nouvelle méthode de modification je suis obligé de la surcharger
Et là ou c'est grave c'est grave c'est que je risque d'oublier de le faire lors de ma prochaine mise à jour de la lib qui contient le nouveau contrat
Ou alors j'ai mal saisi la problématique
[^] # Re: javascript
Posté par allcolor (site web personnel) . Évalué à 2.
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 2.
http://linuxfr.org/comments/1000494.html#1000494
Sauf que dans ta classe tu encapsules ou tu hérites d'une collection de l'api de base.
Donc si ca n'est pas prévu de base tu doit te coltiner de participer au JCP ou reécrire toi-même de toute pièce ta collection.
Ca devient lourdingue pour une simple optim en 2 lignes avec un
Faut arrêter un peu la mauvaise foi aussi
[^] # Re: javascript
Posté par allcolor (site web personnel) . Évalué à 2.
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 2.
Mais la solution que tu défendais ici n'est pas viable.
Heureusement que les inner class sont apparues donc.
[^] # Re: javascript
Posté par benoar . Évalué à 4.
getBounds(Array, Min, Max)
C'est du Prolog, et il n'y a pas d'histoire d'argument en entrée ou retourné, car souvent le "sens" des variable peut être changé comme on le veut ... Pas de problème de nommage de "valeurs de retour", etc.
Bon, c'est typé bizarrement, c'est pas objet, et c'est vieux, mais ça a quand même certains avantages ...
[^] # Re: javascript
Posté par totof2000 . Évalué à 2.
Même plus besoin d'OS ça tourne sur l'Openfirmware de ma sun ...
[^] # Re: javascript
Posté par Alex . Évalué à 1.
C'est peut -être plus lourd mais par la suite tu voudra aussi l'écart type, la variance et ta belle solution de multi-liste t'obligera à un moment à tout refactoriser ton code appelant.
Mouais, faire une belle archi avec tout les beaux patterns que tu veux pour essayer d'éviter les pièges c'est très bien. Chercher l'excellence en essayant de gérer des cas improbables c'est le meilleur moyen d'avoir le code le plus imbittable qui soit, et tout le temps que tu pourrais perdre lors d'un refactoring, tu le perds à gérer la lourdeur de ton archi.
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 2.
Mais lorsque tu crées un toolbox ou framework qui est utilisé par des clients autres que toi, ils préfèrent nettement que toi tu aies visé l'excellence plutôt qu'être obligé de refactorer eux, sinon ils vont voir ailleurs.
[^] # Re: javascript
Posté par Alex . Évalué à 1.
Pour un framework, c'est également discutable. C'est vrai que dans la plupart des cas, j'aime que les dev du dit framework aient pensé adaptable, généralisable. Néanmoins j'aime également aller au plus simple sans avoir à parcourir à chaque fois la doc.
[^] # Re: javascript
Posté par Moonz . Évalué à 3.
Comme quand tu modifies le nombre d'arguments d'une méthode. C'est vraiment crade Java, ça te permet de mettre plusieurs arguments !
[^] # Re: javascript
Posté par CrEv (site web personnel) . Évalué à 2.
utilisation de private computeMinMax http://linuxfr.org/comments1000491.html#1000491
[^] # Re: javascript
Posté par Antoine . Évalué à 3.
Mon dieu mon dieu...
Dans un langage objet, tout est objet y compris les fonctions, les classes et les méthodes (cf. Python), que ce ne soit pas le cas en Java est un autre sujet.
[^] # Re: javascript
Posté par briaeros007 . Évalué à 1.
C'est beau l'objet, mais bon un moment il faut quand même revenir à des paradigmes précis si on veut discuter. On est pas les schtroumpfs, on comprends pas que tu parle d'un "objet fonction" plutot qu'un "objet attribut" ou encore un "objet interface" si tu dis juste "objet".
[^] # Re: javascript
Posté par Antoine . Évalué à 4.
??? Je ne comprends pas ta phrase.
C'est beau l'objet, mais bon un moment il faut quand même revenir à des paradigmes précis si on veut discuter.
Eh bien, "objet", c'est précis : il y a des méthodes, des attributs, un passage par référence (en Python), etc. Une fonction, c'est simplement un object qui implémente la méthode __call__.
Ce que je voulais dire en répondant au zozo du dessus, c'est que ce n'est pas parce qu'un langage est "objet" (et Ruby et Python sont beaucoup plus "objet" que Java) que tout s'écrit sous forme de déclarations de classes et de méthodes.
[^] # Re: javascript
Posté par briaeros007 . Évalué à 2.
J'avais pris ton commentaire pour quelqu'un qui rappel les "bons mots" (comme arroseur pour spammeur et les conneries comme ça) quand que ça complique tout ;)
??? Je ne comprends pas ta phrase.
C'est que j'aime bien compliquer.
Ce que j'essaie de dire, c'est que le terme "fonction" utilisé pour un objet (spécifique) n'est qu'une métonymie.
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 1.
(et Ruby et Python sont beaucoup plus "objet" que Java)
J'affectionne beaucoup python mais faut rien exagérer.
Le duck typing n'est pas ce qu'on appelle de l'objet. C'est un truc batard , pratique, mais qui ne correspond en rien à la POO et à la notion de classification.
Je ne parlerai même pas de l'encapsulation qui n'est pas permise puisqu'on n'a pas de vraie notion de champ privé et encore moins de protected. Et après on t'expliquera que ca n'est pas nécessaire un peu comme les javaistes t'expliquent comment te passer du retour de valeurs multiples.
Je ne m'aventurerai pas non plus sur le terrain du multi-héritage en comparant son modèle à celui du C++ qui adresse presque tous les pbs lié à ce modèle (le membre partagé, ....).
Sans parler de l'autre chose qui n'a rien a voir avec la POO mais qui reste désagréable et sur lequel on n'a pas mal trollé ici.
Tu sais cet acronyme en 3 lettres qui G.I.L ne sera jamais remis en question car ca casserai tout ce bel édifice.
Là aussi on on nous explique que ca sert à rien
Les langages pur objet ce sont en général Smalltalk peut-être Ruby, ceux la même qui sont réputés pour leur piètre performances.
Java, C++ ont fait le choix du compromis entre performance et purété, par exemple en introduisant des type primitifs non purement objet.
Bref, le langage miracle n'existe pas.
[^] # Re: javascript
Posté par Ontologia (site web personnel) . Évalué à 1.
Comme quoi c'est possible, ça demande juste un compilateur qui analyse globalement son code.
Citons aussi SmartEiffel, qui est beaucoup plus pur que Java et qui offre de bonnes performances.
Avant lui, il y a eu Self, le premier langage à proto, sur lesquel il y eu énormément de travaux sur les perfs d'un tel langage - absolument pur, en passant -
Ces travaux (ainsi que les précédents) sont à l'origine des JIT actuelles.
http://www.research.sun.com/research/jtech/pubs/97-pep.ps
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 2.
Au moment ou j'ai écris le langage miracle n'existe pas , j'étais sur que tu allais nous ressortir Lisaac
Il n'y a a pas de véritable consensus sur les limites exacts d'OO.
Les contrats en font ils partie, le mutli héritage, les exceptions
Chaque langage a ses spécificités et l'Objet ne répond pas à tous les besoins.
Le duck typing ne respecte pas l'objet mais personne n'a réussi à me démontrer que ca n'était pas plus efficace dans bien des cas.
D'ailleurs il s'apparente de près au concept d'interface en Java, le contrôle statique en moins et a souplesse en plus.
L'AOP adresse les problèmes transversaux que l'approche objet n'a jamais su gérer autrement qu'au prix de frameworks gargantuesques et complexes
Les langages déclaratifs à la Prolog se révélent d'une redoutable efficacité lorsque l'algorithmie montre ses limites.
Encore une fois il faut la pureté objet ne doit pas être une fin en soi.
[^] # Re: javascript
Posté par Nicolas Boulay (site web personnel) . Évalué à 2.
L'AOP adresse les problèmes transversaux que l'approche objet n'a jamais su gérer autrement qu'au prix de frameworks gargantuesques et complexes
Il existe un article qui dis le contraire où chaque fonction de l'aop est remplacé par un pattern plus simple à gérer en objet.
Les langages déclaratifs à la Prolog se révélent d'une redoutable efficacité lorsque l'algorithmie montre ses limites.
Tu as des exemples d'utilisations "industriel" (en dehors des labos de compilateur ou de recherche en informatique) ?
"La première sécurité est la liberté"
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 2.
Il existe un article qui dis le contraire où chaque fonction de l'aop est remplacé par un pattern plus simple à gérer en objet.
Et quel article STP.
Ca m'intéresse
[^] # Re: javascript
Posté par Bozo_le_clown . Évalué à 1.
Au fait je croyais que Lisaac était un langage orienté prototype et pas un langage orienté objet
http://fr.wikipedia.org/wiki/Programmation_orient%C3%A9e_pro(...)
[^] # Re: javascript
Posté par Nicolas Boulay (site web personnel) . Évalué à 2.
La programmation orientée prototype est une forme de programmation orientée objet sans classe, basée sur la notion de prototype...
"La première sécurité est la liberté"
[^] # Re: javascript
Posté par Antoine . Évalué à 3.
Si je comprends bien, les langages à prototype comme Javascript ne sont pas non plus estampillés "POO" parce qu'ils ne correspondent pas à ta notion de classification ?
On peut voir le duck-typing au contraire comme définissant une classification de fait. C'est vrai qu'en Java il faut tout déclarer...
Je ne m'aventurerai pas non plus sur le terrain du multi-héritage en comparant son modèle à celui du C++ qui adresse presque tous les pbs lié à ce modèle
En français, on n'adresse pas des problèmes, on les résoud.
Sinon, l'héritage multiple de Python correspond à l'héritage "virtuel" de C++, je ne vois pas trop où se situe la différence. Si tu as besoin d'un héritage multiple non-virtuel, c'est AMHA que tu devrais faire de la délégation plutôt que de l'héritage.
Tu sais cet acronyme en 3 lettres qui G.I.L ne sera jamais remis en question car ca casserai tout ce bel édifice.
Effectivement, ça tient 1) du hors-sujet 2) du troll mal informé, puisqu'il y a des implémentations de Python sans GIL et qui pourtant respectent la sémantique du langage.
Java, C++ ont fait le choix du compromis entre performance et purété
Là ça me fait marrer, la raison pour laquelle Java a des performances acceptables aujourd'hui, c'est qu'un tas d'ingénieurs est payé à temps plein depuis plus de dix ans pour ça. Mettre C++ dans le même sac de ce point de vue est grotesque.
# Explicit is better than implicit.
Posté par benoar . Évalué à 10.
Explicit is better than implicit.
Et j'ai beau aimer perl aussi pour pas mal de ses constructions, au final ce coté "super puissant" est souvent plus emmerdant qu'autre chose.
La preuve ? Ton exemple :
@liste = %h{@t};
ne marche pas chez moi, il fallait écrire (je suppose) :
@liste = @h{@t};
Voilà, c'est ce genre de détail qui me fait m'énerver sur perl.
En python, ça aurait donné (avec la compréhension sur les listes) :
liste = (h[k] for k in t)
ce qui est, quoique un peu plus long, tout de même beaucoup plus explicite et lisible.
Sinon, ton histoire de pouvoir utiliser des listes là où on utilise des valeurs, il me semble me rappeler que beaucoup de monde en a déjà parlé (j'y avait pensé il y a quelques années déjà) mais qu'au final ça apporte peu par rapport au bazar qu'il faut faire pour l'intégrer. En gros, c'est faire un map() implicite, et comme je disais plus haut, "explicite c'est mieux qu'implicite" ...
[^] # Re: Explicit is better than implicit.
Posté par CrEv (site web personnel) . Évalué à 2.
Je crois que c'est le truc qui m'a toujours fait détesté python.
Pourquoi écrire du code alors que c'est évident ?
Ca complique la vie du codeur, ça complique aussi la vie de tous ceux qui lisent le code et ça n'apporte rien...
open(FILE, ">file.txt");
while(<FILE>) {
print if =~ /plop/
}
close(FILE);
C'est implicite et lisible si tu connais =~ et < >
[^] # Re: Explicit is better than implicit.
Posté par Victor STINNER (site web personnel) . Évalué à 9.
Évident, c'est pas gagné, surtout avec Perl qui contient énormément de règles implicites qu'il faut connaître pour comprendre le code (il me semble que Ruby et Ruby on rails fonctionnent pareil). L'avantage d'un code explicite est que n'importe qui (ayant une connaissance minimale du langage) peut comprendre facilement le code et donc : le corriger et l'améliorer. D'une manière générale, un code explicite est un gage de pérénité : si le développeur disparait, on peut le remplacer.
[^] # Re: Explicit is better than implicit.
Posté par Sytoka Modon (site web personnel) . Évalué à -2.
Je ne comprends rien aux programmes Java avec leur millions de lignes, leur millions de classe, les fichiers de conf XML de Tomcat ;-)
J'ai travaillé avec pas mal de personne qui n'avait jamais fait de Perl, qui n'en pensait que du mal mais qui avait fait du PHP ! Et bien, tous ont compris de suite les programmes ! Evidement, il y a quelques règles à respecter pour avoir du Perl lisible mais c'est pareil dans tous les langages.
Sinon, il y a des milliers de modules sur le CPAN et la doc est très claire pour les utiliser. Je n'ai pas vraiment de soucis avec les paramètres.
Au niveau objet, je ne sais pas pourquoi le mot clef 'class' n'a pas été intégré pour faire plaisir aux gens. A mon avis, c'est pas si difficile à faire pour les bons programmeurs Perl. Mais pour les gens comme moi, on peut déjà utiliser Moose ou Mouse et c'est pas plus dur que de faire une classe en Java.
[^] # Re: Explicit is better than implicit.
Posté par CrEv (site web personnel) . Évalué à 2.
Oui mais quand je dis ça je veux dire que le code évident (parce qu'il l'est réellement, que c'est redondant, qu'il y a suffisament d'informations pour le comprendre) peut être supprimé.
Mais à chaque fois qu'on parle de perl, l'argument avancé pour les "contre" est qu'il est illisible alors qu'en réalité c'est que les gens ne le connaissent pas.
> n'importe qui (ayant une connaissance minimale du langage)
Où s'arrête le minimal ?
Les $* font partie de perl et du minimum de perl pour moi.
Le truc c'est que vous ne voulez pas apprendre perl car il semble obscure et il semble obscure car vous ne l'apprenez pas.
Demandez à un programmeur lisp de coder en java et il va dire qu'il ne comprend rien.
En fait tout le monde est trop formatté au c/c++/java je trouve...
> un code explicite est un gage de pérénité : si le développeur disparait, on peut le remplacer.
Je ne pense pas.
SI je file dans quelques année un code perl 4 ou 5 à un développeur avec un bouquin du perl correspondant alors mon code serait maintenable également.
Si je file à un programmeur ne connaissant pas python un programme en python, c'est pas sur qu'il s'en sorte plus facilement.
Evidemment si je file un code pourris en perl il y aura de la casse, mais du code crade on peut en écrire dans quasiment tout langage.
Il n'y a qu'à voir ce qu'on peut faire en C:C++... et pourtant y'a pas trop de magie comme dans perl.
Tiens d'ailleurs c'est pas mal ça, si dans quelques années on file un programme C++ (avec tout plein de pointeurs) à un programmeur java je voudrais bien voir ce que ça donnera...
Explicit is better than implicit est une erreur à mon avis...
[^] # Re: Explicit is better than implicit.
Posté par manatlan (site web personnel) . Évalué à 9.
Qu'importe le language ... mais que tu donnes ton code à qqu'un d'autres, que tu le reprennes 3 ans plus tard, où que tu codes après qques bieres.
Le côté explicit d'un algo, d'une formule, d'une conditionnel est vital, pour se mettre/remettre dans le bain. L'implicite necessite que la personne, ou toi, re-devine ce que tu voulais dire/faire "en codant ainsi", et gaspille ses neurones plutôt que de les concentrer dans l'action à réaliser ... et souvent c'est pas gagné/facile.
Le python, pour ça est vraiment sur LA bonne voie ...
Maintenant, qqsoit le language on peut écrire cradement (c'est moins vrai pour le python ;-). ça on est d'accord ... Mais il y a quand même des languages propices pour des écritures vraiment abstraites. Ruby avec ses différentes syntaxes pour écrire une même conditionnelle d'égalité. Perl avec toutes ces choses "implicites à connaître" (et magiques) n'aident pas.
Ok, mieux vaut avoir des règles dans le travail collaboratif avec ce genre de language (plus que dans d'autres languages). Mais, dans la vraie vie, sous la pression, sous le stress, sous les contraintes, et pour aller vite ... tu zappes les règles et tu peux faire d'énormes raccourcis (pk le language le permet), qui te couteront plus tard. C'est une prise de risque supplémentaire et inutile.
Perso, j'ai bien tenté de me mettre à ruby, mais ces différentes syntaxes pour exprimer la même chose, et tous ces hiéroglyphes (et caractères qu'il faut shifté pour insérer) m'ont fortement rebuté ... il fallait "trop apprendre", par rapport à des choses plus classiques ("formatté au c/c++/java").
Le python a également l'avantage de s'écrire comme tu écris en algorythmie (si ... sinon ... alors) ... pour ma part : ça FIT my brain à la perfection.
[^] # Re: Explicit is better than implicit.
Posté par CrEv (site web personnel) . Évalué à 2.
> L'implicite necessite que la personne, ou toi, re-devine ce que tu voulais dire/faire "en codant ainsi"
Implicite ne veut pas dire de supprimer tout ce qui est possible hein.
On peut avoir aussi bien de l'"explicite" et de l'"implicite" dans un même programme.
Après faut juste coder intelligemment...
Permettre d'utiliser l'implicite ne veut pas dire tout supprimer. Si vous ne voulez pas coder proprement, c'est pas le langage qui empêchera de faire de la merde.
Mais si quelque chose est _évident_ (que ce soit au moment où on l'écrit, au moment où on le lit, même plus tard) pourquoi l'écrire ?
Utiliser de l'implicite ne veut pas dire ne pas documenter, supprimer tout ce qui traine et faire du code idiot hein !
> Mais, dans la vraie vie, sous la pression, sous le stress, sous les contraintes, et pour aller vite ... tu zappes les règles et tu peux faire d'énormes raccourcis (pk le language le permet), qui te couteront plus tard.
C'est bien pour ça qu'il existe des outils pour contraindre, des outils de vérification de syntaxe par exemple (éviter par exemple qu'il existe des blocs sans accolades)
> il fallait "trop apprendre", par rapport à des choses plus classiques ("formatté au c/c++/java").
Ben voilà le vrai problème, refuser des avancées parce qu'il faut apprendre...
[^] # Re: Explicit is better than implicit.
Posté par manatlan (site web personnel) . Évalué à 3.
attention ! double négation ... on peut simplifier : "Utiliser de l'implicite veut dire documenter"
et c'est tellement vrai ...
et dans la vraie vie, sous la pression, sous le stress, sous les contraintes, et pour aller vite ... tu zappes le commentairage de l'énorme raccourci implicite que tu viens de coder pour te faire plaisir.
> Mais si quelque chose est _évident_ (que ce soit au moment où on l'écrit,
> au moment où on le lit, même plus tard) pourquoi l'écrire ?
faut toujours penser à celui qui reprendra ton code, ou à toi, avec qques bieres dans le nez.
faut être le plus clair possible, ça paye vraiment avec le temps
> C'est bien pour ça qu'il existe des outils pour contraindre, des outils
> de vérification de syntaxe par exemple (éviter par exemple qu'il existe
> des blocs sans accolades)
je ressort mon argument qui va très bien là également :
dans la vraie vie, sous la pression, sous le stress, sous les contraintes, et pour aller vite ... tu zappes le lancement régulier de ton "outil pour contraindre" ... (et là, c'est encore plus vraie)
>> il fallait "trop apprendre", par rapport à des choses plus
>> classiques ("formatté au c/c++/java").
>Ben voilà le vrai problème, refuser des avancées parce qu'il faut apprendre...
oui, je dis pas ... c fun/hype de faire du ruby, du erlang, du <ton language préféré> ...
mais imagine la cata si chaque personne utilisait un language différent ... bonjour l'interop;-)
la syntaxe est une chose, et si elles se ressemblent inter-languages, c'est quand même aussi dans le but de simplifier l'appréhension du language nouveau.
Les avancées significatives ne sont pas la syntaxe du language, mais dans la sémantique.
[^] # Re: Explicit is better than implicit.
Posté par CrEv (site web personnel) . Évalué à 2.
mais imagine la cata si chaque personne utilisait un language différent
Donc il ne faut pas utiliser python non plus !
> la syntaxe est une chose, et si elles se ressemblent inter-languages, c'est quand même aussi dans le but de simplifier l'appréhension du language nouveau.
Mais c'est bien ça le problème, on peut aussi appeler ça un nivellement par le bas. Et non, un langage ça _doit_ s'apprendre.
Il faut savoir perdre du temps (à apprendre) pour devenir plus performant, pour faire des choses plus puissantes et donc gagner du temps sur du moyen terme...
> je ressort mon argument qui va très bien là également
Ben en fait non, je trouve pas vraiment que ce soit un bon argument...
(et pour les tests, outils, etc ça va par exemple être des lancement automatiques sur build / commit donc je les lance pas à la main, manquerait plus que ça...)
> faut toujours penser à celui qui reprendra ton code, ou à toi, avec qques bieres dans le nez.
faut être le plus clair possible, ça paye vraiment avec le temps
Déjà dans mon taff j'évite vraiment de coder avec de la bière, et si c'est le cas et que je comprend pas mon code, je crois qu'il faut plus en vouloir à la bière qu'au code...
Et faire de l'implicite n'empêche absolument pas de faire clair.
Allez, juste pour le fun :
faire de l'explicite inutile (sous pretexte que c'est "better") complexifie inutilement le code et tend à le rendre moins clair.
Moins il y a de parasitage dans le code, plus le code est clair et compréhensible.
[^] # Re: Explicit is better than implicit.
Posté par Bozo_le_clown . Évalué à 5.
Donc il ne faut pas utiliser python non plus !
Ben si, puisque c'est ce qui ressemble le plus à un langage ....naturel:
L'anglais.
Bon je suis de la vieille école, mais lorsque j'ai appris l'informatique on avait l'habitude d'écrire un truc avant de coder comme des fous. Ca s'appelait un algorithme et après on le traduisait en Pascal.
J'avoue que lorsque je lis du code python, j'ai l'impression de lire mes bons vieux algos procéduraux.
C'est grave docteur ?
Mais c'est bien ça le problème, on peut aussi appeler ça un nivellement par le bas. Et non, un langage ça _doit_ s'apprendre.
Il faut savoir perdre du temps (à apprendre) pour devenir plus performant, pour faire des choses plus puissantes et donc gagner du temps sur du moyen terme...
Non ce qu'il faut apprendre c'est des concepts, des contsructions des paradigmes et pouvoir les retrouver dans un ou des langages.
Qu'est qu'un "choix de" une boucle "tant que", une condition
Qu'est-ce qu'une fonction, une procédure, un objet, une classe une fermeture lexical, une clause, un aspect...
Mais surtout comment bien utiliser ces concepts.
Quand utiliser le polymorphisme, quand utiliser l'héritage au lieu d'une composition, un singleton ou tout autre design pattern.
Savoir qu'utiliser une table de mappage va booster mes perfs pour la recherche d'un info plutôt que d'itérer sur une liste surtout si cette liste est beaucoup accédée en lecture et peu en écriture.
Par contre passer mon temps à me demander quand le dernier contexte a été modifié ou où est-ce que j'ai pu oublier cette putain d'apostrophe qui me pète ma regexp, j'avoue que ca me fait moyennement triper.
[^] # Re: Explicit is better than implicit.
Posté par Ontologia (site web personnel) . Évalué à 3.
http://www.weitz.de/regex-coach/
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: Explicit is better than implicit.
Posté par Bozo_le_clown . Évalué à 2.
Avec python tout va très bien, merci.
[^] # Re: Explicit is better than implicit.
Posté par plagiats . Évalué à 1.
[^] # Re: Explicit is better than implicit.
Posté par CrEv (site web personnel) . Évalué à 3.
> L'anglais.
Ha bon ?
Je te conseil de lire ce qu'écrit Larry Wall (le créateur de perl) à propos de perl 5, des langages (ça se trouve dans un bouquin sur perl, chez oreilly) ça te surprendra surement sur la création de perl.
A noter aussi que Larry Wall est à la base un linguiste.
Mais je sais pas si c'est possible en python, mais écrire quelque chose de proche du langage naturel en perl et ruby c'est extrêmement simple :
print line if line.include? "plop"
Affiche la ligne si la ligne contient "plop"
Comment écrire ça plus simplement ?
Mais l'avantage est qu'on peut aussi écrire l'inverse très facilement et toujours de manière très compréhensible :
print line unless line.include? "plop"
C'est beaucoup plus logique que "if !line.include? "plop"" ou "if not line.[...]"
Et si certains ne comprennent pas au premier abord, ben à part leur faire apprendre le mot unless on peut pas faire grand chose je trouve.
Et bon, le coup de python c'est proche du langage naturel... mouaif, faut voir hein ...
Allez, une abération que j'ai jamais supporté dans python :
pourquoi se trimbaler "self" dans la définition d'une méthode d'un objet ?
Ok, explicit better gnia gnia gnia
Le programme / les développeurs sont trop con pour savoir qu'une méthode qui se trouve dans la définition d'un objet est lié à un objet ?
Ca pue surtout le modèle objet un peu foiré ça...
(tout n'est probablement pas parfait en ruby, mais de là à mettre python comme le sauveur...)
[^] # Re: Explicit is better than implicit.
Posté par MsieurHappy . Évalué à 3.
Ce qui me parait bien plus essentiel, c'est que les concepts de bases du langage soit simples et génériques. Typiquement à la Lisp et à la Haskell (et peut-être Smalltalk, mais je ne le connais pas vraiment).
Un langage ne doit pas être «intuitif» mais rendre facilement exprimable les algorithmes. Et si il faut assimiler des concepts avant, soit. Je pense donc qu'un bon langage de programmation doit plus s'approcher d'un langage mathématique que d'un langage naturel.
[^] # Re: Explicit is better than implicit.
Posté par Bozo_le_clown . Évalué à 3.
Je préfère nettement me taper le tuto de Guido en 2h en me disant que je sais presque tout faire avec ca et passer le reste du temps gagné à dévorer un roman de SF que me taper 20 h sur les Perl O'Reilly.
Sinon hormis ton cas d'ecole, ceux auxquels j'ai été confronté ressemblent plus à ca:
s/^\^Q //;
$longueur_ligne = length($_);
$caractere_fin_ligne = $longueur_ligne ? ord(substr($_,$longueur_ligne-1,1)) : 0;
....
my @c= ;
close Fi;
map s/[\r\n]+/\n/g, @c;
open (Fi,">$f") or die;
print Fi @c;
Ce n'est pas le plus complexe mais de là à parler de langage naturel.
Heureusement que j'ai insisté pour que le gars qui a pondu ca donne de noms de variables explicites et commente un peu parce le decryptage permanent avec le perlref sous la main au bout de 200 lignes ca devient un peu lassant.
Et je te passe sur les effets de bord
[^] # Re: Explicit is better than implicit.
Posté par windu.2b . Évalué à 8.
On dirait des injures censurées d'une BD...
C'est là toute la différence avec Java, qui est peut-être verbeux mais qui fait plus penser aux injures du capitaine Haddock : on en a plein la bouche, de tous ces mots !
:-D
[^] # Re: Explicit is better than implicit.
Posté par Jean B . Évalué à 2.
pourquoi se trimbaler "self" dans la définition d'une méthode d'un objet ?
Ok, explicit better gnia gnia gnia
Le programme / les développeurs sont trop con pour savoir qu'une méthode qui se trouve dans la définition d'un objet est lié à un objet ?
Ca pue surtout le modèle objet un peu foiré ça...
C'est un héritage du modèle objet de en:Modula-3.
Il y a effectivement pas mal de langages ou il est implicite, mais bien souvent ça entretient une confusion sur son statut, ses possibilités, ...
Au moins en Python les choses sont claires, l'instance est un argument comme les autres (on peut le nommer toto si ça nous chante).
Voir self/this comme un argument est très pratique pour exploiter pleinement l'héritage multiple par exemple:
class Foo(object):
def bar(self, arg0):
print self, arg0
foo = Foo()
foo.bar('baz')
# <__main__.Foo object at 0x7f22d6d0aef0> baz
Foo.bar(1)
# TypeError: unbound method bar() must be called with Foo instance as first argument (got str instance instead)
Foo.bar(foo, 'baz')
# <__main__.Foo object at 0x7f22d6d0aef0> baz
class Qux(object):
def bar(self, arg0):
print 'Qux !'
class Fum(Foo, Qux):
pass
Fum().bar('egg')
# <__main__.Fum object at 0x7f22d6bfa7d0> egg
class Fum(Foo, Qux):
def bar(self, *args, **kwargs):
return Qux.bar(self, *args, **kwargs)
Fum().bar('egg')
# Qux !map(Foo.bar, [Fum()] * 2, ['egg', 'spam'])
# <__main__.Fum object at 0x7f22d6c5c490> egg
# <__main__.Fum object at 0x7f22d6c5c490> spam
Et tu peut même intervenir dans l'autre sens quand tu commence à taper dans les __new__ et autres __metaclass__.
[^] # Re: Explicit is better than implicit.
Posté par benoar . Évalué à 2.
Bon, je pourrais te sortir pas mal de phrases du Zen pour dire que je n'aime pas ton exemple (je suis pour une écriture "naturelle", mais dans une certaine limite, quand elle n'apporte pas de redondance) :
Special cases aren't special enough to break the rules.
There should be one-- and preferably only one --obvious way to do it.
Quand tu te mets à apporter plein de raccourcis déjà dispo sous une autre forme, tu compliques le langage. Bon, ne me dis pas de faire de l'assembleur, ce que je veux dire c'est qu'il y a un équilibre à trouver, et je trouve que python en a trouvé un très bon. Et je pense que la deuxième phrase que je viens de citer est explicitement dirigée "contre" Perl.
Sinon, ça me fait marrer que tu parles de complexité car le langage est plus "épuré" : au contraire, tu vois la complexité dans le fait que le code est "plus long", mais moi je trouve qu'un langage avec plus de constructions (pas forcément super utiles) est vraiment plus complexe à apprendre. Le seul raccourci qui me manque dans python est les regexp "intégrées", mais bon, je m'en passe assez facilement. Et c'est ce qui me donne envie de regarder vers ruby ... mais son coté Perl me fait peur ...
[^] # Re: Explicit is better than implicit.
Posté par totof2000 . Évalué à 2.
Pas forcément.
A l'utilisation, tu peux te limiter à quelques constructions qui te permettront de couvrir tous les cas que tu traiteras. Par contre effectivement, lorsque quelqu'un n'a pas le même "style" de codage que toi, c'est pas toujours simple à comprendre mais on s'y fait à force.
Et c'est ce qui me donne envie de regarder vers ruby ... mais son coté Perl me fait peur ...
Vas-y, Ruby pour moi est un bon compromis entre la souplesse de Perl et la raideur de Python. Il est surtout beaucoup plus lisible pour quelqu'un qui connait pas trop le langage.
[^] # Re: Explicit is better than implicit.
Posté par benoar . Évalué à 4.
Plus lisible que Perl ou Python ?
S'il y a bien un truc dont je suis quasi-sûr par beaucoup d'expériences, c'est que Python est un des langages les plus lisibles qu'il y ait pour ceux qui ne le connaissant pas.
[^] # Re: Explicit is better than implicit.
Posté par totof2000 . Évalué à 3.
Plus lisible que perl, c'est sur. Par rapport à Python, il s'en rapproche beaucoup. Les concepts d'objet sont beaucoup plus simple à appréhender. Pour moi c'est le juste milieu.
S'il y a bien un truc dont je suis quasi-sûr par beaucoup d'expériences, c'est que Python est un des langages les plus lisibles qu'il y ait pour ceux qui ne le connaissant pas.
Il y a des chances, et je pense que pour toi Ruby sera juste un cran en dessous, mais te permettra de faire certaines choses plus simplement qu'en Python en raison de la souplesse du langage.
[^] # Re: Explicit is better than implicit.
Posté par ckyl . Évalué à 2.
Ca marche bien quand tu es tout seul et sur une période assez courte (< 2 ans).
Dans une vraie équipe, chacun à beau se limiter, la somme des limitations reste tout de même un gros bordel. Je bosse actuellement sur un projet qui a vu 71 devs en 10 ans, moins y'a de cowboy dans le lot mieux je me porte.
[^] # Re: Explicit is better than implicit.
Posté par totof2000 . Évalué à 2.
Oui, cela dit (en tout cas je parle pour moi) : plus j'utilise un langage, et plus j'écris du code "efficace". Donc, plus ça vient et moins je me limite.
Je bosse actuellement sur un projet qui a vu 71 devs en 10 ans, moins y'a de cowboy dans le lot mieux je me porte.
Il est vrai que je ne développe pas de la même façon lorsque je bosse pour un truc qui ne sera jamais maintenu par personne d'autre que moi .....
[^] # Re: Explicit is better than implicit.
Posté par CrEv (site web personnel) . Évalué à 2.
Mais je vois en fait le langage (et sa complexité surtout) comme un investissement.
Si apprendre un langage un peu plus complexe, et donc "perdre" du temps dessus, me permet, à chaque fois que j'en aurai besoin, de me simplifier la vie, de simplifier mon code, sa compréhension, etc, alors j'estime que ça en vaut la peine.
Comme je dis de temps en temps, il faut savoir (apprendre ...) à perdre du temps maintenant pour en gagner plus tard.
Et c'est pour ça que j'aime les langages assez expressifs (je sais pas si c'est le bon terme) qui ne sont pas pauvres en mot clés (mais qui restent compréhensibles)
> Et c'est ce qui me donne envie de regarder vers ruby ... mais son coté Perl me fait peur ...
En fait moi c'est presque l'inverse.
j'adore ruby parce qu'il est puissant, expressif mais n'a pas les travers de perl tout en reprenant ses bons côté (les unless, les regexp, etc) et des trucs hyper sympa comme pouvoir mettre des "?" et "!" à la fin des noms de méthodes.
Je trouve les programmes ruby assez propre (même si on peut faire du crade hein...) plus lisible que perl.
Je viens de lire qq news sur python et dans le genre pas facile à comprendre par exemple :
5 // 10
si qqn qui n'a jamais utilisé ça se trouve devant, je suis pas sur que ce soit compréhensible directement (histoire de division entière, etc)
[^] # Re: Explicit is better than implicit.
Posté par benoar . Évalué à 4.
J'ai déjà fait du Perl à une époque. Et bien l'histoire des %@$ je suis perdu aujourd'hui. Ta mémoire n'est pas infinie, et ce que tu passes comme effort à un moment, si tu l'oublies au bout d'un moment, ça ne sert pas à grand chose. En python, je n'ai quasiment jamais rien oublié, même après pas mal de temps à ne pas en avoir fait.
Sinon, pour l'histoire des divisions, c'est quelque chose qui doit être exceptionnel d'utiliser cette syntaxe, car le moto du python est que ça fasse les choses "bien" par défaut. Il y a eu une erreur historique sur la division (par défaut entière en 2.x, flottante en 3.x), maintenant c'est reglé.
[^] # Re: Explicit is better than implicit.
Posté par Sytoka Modon (site web personnel) . Évalué à 1.
> pour le python ;-). ça on est d'accord ...
Ben je suis désolé mais je n'y comprends rien en Python. J'ai même du balancé un site web en Zoppe pour faire du SPIP car Python me gonflait plus que la normale, et pourtant je déteste le PHP qui n'aurait jamais du exister car c'était du sous perl.
Non, le Python n'est pas mieux que les autres, il a ses fans mais il a aussi des inconvénients comme les autres.
Pour me changer les idées, je me suis mis à Erlang et là au moins, on change de perspective. C'est amusant.
[^] # Re: Explicit is better than implicit.
Posté par benoar . Évalué à 5.
[^] # Re: Explicit is better than implicit.
Posté par David Carlier . Évalué à 3.
[^] # Re: Explicit is better than implicit.
Posté par Yusei (Mastodon) . Évalué à 2.
C'est marrant, pour moi les différentes syntaxes sont un atout, car elles permettent d'écrire du code auto-documenté. En partique, "if" et "unless" servent à la même chose, mais utilisés correctement ils rendent le code plus clair:
- if: si une condition est vraie, on fait ce bout de code
- unless: généralement on ne fait pas ce bout de code, sauf si...
De même, "while" et "until" servent à la même chose mais dans des conditions différentes. Ce sont de petites nuances qui, pour moi, facilitent la lecture du code, parce que ça permet de mettre l'accent sur ce qui est important.
Toujours dans la même idée, j'aime pouvoir écrire "5.times" pour une boucle qui doit s'exécuter 5 fois, "0.upto(4)" pour une boucle qui va de 0 à 4 et "tab.each" pour une boucle qui parcourre un tableau. Ce sont pour moi trois écritures qui mettent l'accent sur ce qu'on veut faire, et les trois ont des raisons d'exister.
Quel est le bout de code qui demande le plus de réflexion entre les deux suivants ?
for (int i=5 ; i >= 0; i--) {
printf("%d\n", i);
}
5.downto(0) { |i|
print "#{i}\n"
}
Ce sont deux bouts de code très simples, donc n'importe qui de familier avec la syntaxe des langages les comprend très vite. Dans les deux, je dois regarder la valeur de début, la valeur de fin et le nom de la variable. Mais dans le code en C, je dois regarder le sens de la condition, est-ce que c'est supérieur strict ou égal, et quel est l'incrément, pour vérifier ce que la boucle fait. En ruby, on écrit explicitement "down to", et donc je ne peux pas avoir de doute.
Après, plusieurs manières d'écrire les choses ça peut vouloir dire plus de choses à apprendre pour comprendre le code des autres. C'est le cas en Perl. En Ruby, je ne suis pas d'accord. Prenons les exemples que j'ai donnés pour les boucles: pour peu qu'on parle anglais, les trois sont parfaitement explicites et ne demandent pas d'explication. N'importe qui comprendra que "5.times" va faire quelque chose cinq fois. De même pour "0.upto(4)", "4.downto(0)" et autres.
[^] # Re: Explicit is better than implicit.
Posté par Antoine . Évalué à 3.
Pas d'accord. Si tu lis upto(4) ou downto(0), il n'y aucun moyen de savoir (autre que d'apprendre le langage) si cela s'arrête à 3 ou à 4, à 0 ou à 1 (voire à -1).
Bref, c'est un joli raccourci, mais ça ne simplifie rien.
[^] # Commentaire supprimé
Posté par Anonyme . Évalué à 4.
Ce commentaire a été supprimé par l’équipe de modération.
[^] # Re: Explicit is better than implicit.
Posté par benoar . Évalué à 1.
[^] # Commentaire supprimé
Posté par Anonyme . Évalué à 2.
Ce commentaire a été supprimé par l’équipe de modération.
[^] # Re: Explicit is better than implicit.
Posté par Anonyme . Évalué à 2.
Demandez donc à un gamin de compter vous verrez qu'il commencera systématiquement à 1. Ce n'est pas pour rien que le zéro est arrivé très tard dans les mathématiques.
[^] # Re: Explicit is better than implicit.
Posté par benoar . Évalué à 3.
As-tu déjà fait du Matlab ? Je trouve imbitable la programation dans ce langage, car tu as toujours des -1 et +1 qui se trimbalent partout. Pas en C (ni en python).
Par exemple, en python, quand tu choisis une sous-chaîne : s[2:4]
Quelle sera la longueur de cette chaîne ? 4-2 = 2
Quelle sera l'index du prochain caractère ? s[4]
Combien de caractères se trouvent avant ? 2
Je sais pas quoi trouver d'autre comme exemple, mais tout ça est pour moi super logique. Fait le avec des intervales autrement, et en indexant à partir de 1, ce sera un bordel immonde.
OK, c'est peut-être une "déformation" initiale, mais après c'est beaucoup plus pratique que la manière "usuelle", et ça les gens ne s'en rendent pas compte car ils ne font pas souvent ce genre d'opération.
[^] # Commentaire supprimé
Posté par Anonyme . Évalué à 1.
Ce commentaire a été supprimé par l’équipe de modération.
[^] # Re: Explicit is better than implicit.
Posté par benoar . Évalué à 2.
Bon, pour les exemples, je sais pas vraiment quoi trouver d'autre ... Allez :
La chaîne de 5 caractères à l'indice x : s[x:x+5]
-> pas besoin de se dire "ha bah comme c'est inclusif, il faut enlever un"
La notation "inverse" : s[-y] == s[len(s)-y]
-> c'est une jolie propriété, je trouve, qui ne marche pas avec l'indexation à 1
Enfin bref, je n'ai plus vraiment d'arguments, mais je n'ai jamais eu à me prendre la tête avec l'indexation à 0 et les "range" [inclus..exclu), alors qu'avec l'indexation à 1, si. Je veux dire, au niveau des calculs ; après, tu peux arguer que c'est moins "naturel", mais quand le naturel est si peu pratique, bah je préfère trouver la solution la "logique".
[^] # Re: Explicit is better than implicit.
Posté par Yusei (Mastodon) . Évalué à 3.
[^] # Re: Explicit is better than implicit.
Posté par Anonyme . Évalué à 2.
Enfin j'avais bien un prof de math qui disait que au dela de 5 dimensions spatiales elle commençait à avoir des problèmes à se représenter la géometrie ... cela montre que l'on a pas tous le même cerveau car moi j'arrive pas à imaginer quoique ce soit au dela de 3...
[^] # Re: Explicit is better than implicit.
Posté par Antoine . Évalué à 3.
(ne me réponds pas qu'il suffit d'itérer l'itérateur N fois...)
[^] # Re: Explicit is better than implicit.
Posté par Antoine . Évalué à 2.
[^] # Re: Explicit is better than implicit.
Posté par Philip Marlowe . Évalué à 1.
for (int i = 5; i < 0; i--)
....
[^] # Re: Explicit is better than implicit.
Posté par Yusei (Mastodon) . Évalué à 3.
Merci de confirmer que la syntaxe du "for" n'est pas claire :)
[^] # Re: Explicit is better than implicit.
Posté par Yusei (Mastodon) . Évalué à 3.
[^] # Re: Explicit is better than implicit.
Posté par briaeros007 . Évalué à 2.
On déclare pas une variable dans un for, mais en début de bloc.
Rahlala faut tout leur apprendre
XD
[^] # Re: Explicit is better than implicit.
Posté par Sufflope (site web personnel) . Évalué à 2.
[^] # Commentaire supprimé
Posté par Anonyme . Évalué à 3.
Ce commentaire a été supprimé par l’équipe de modération.
[^] # Re: Explicit is better than implicit.
Posté par briaeros007 . Évalué à 1.
[^] # Re: Explicit is better than implicit.
Posté par Antoine . Évalué à 5.
C'est implicite et lisible parce que c'est le cas d'école d'utilisation de Perl dans n'importe quel tutorial pour débutants.
Dès qu'on s'éloigne de ce genre de démonstrations de cinq lignes et qu'on cherche à faire autre chose que du parsing à base de regexp, il n'y a plus rien de très attirant dans Perl...
# Perl..? :-s
Posté par Spack . Évalué à 1.
Je vais donc vite fait jeter un œil sur l'article Wikipédia concernant Perl [http://fr.wikipedia.org/wiki/Perl_(langage)] et là je me dis effectivement je n'y connais pas grand chose niveau langage de programmation voir même niveau informatique... Entre les différents sigils [http://fr.wikipedia.org/wiki/Sigil_(informatique)] que j'utilise par exemple en Bash ou PHP sans en connaître le nom et les variables à portées dynamique, lexicale ou celle représentée par le mot clé 'our' [http://fr.wikipedia.org/wiki/Portée_(informatique)], tout ce que j'en est tiré est un mal de crane...
Pourtant je n'avais pas rencontré de difficulté à essayer de comprendre lors de ma rencontre avec le C/C++/Java/Python/Javascript/PHP/etc... C'était des notions que j'arrivais plus ou moins à appréhender...
Mais rien quand lisant les articles de Wikipédia sur Perl et les notions associées, je me rend compte que je suis en fait une bouse infâme :-s
Du coup j'ai toujours voulu essayer Perl mais je pense que je vais m'en tenir à le connaître de nom :-(
[^] # Re: Perl..? :-s
Posté par briaeros007 . Évalué à 1.
Ce que je veux dire, si tu as un script/un programme à faire et que trouve que le bash/awk/grep devient trop compliqué, et que le C trop bourrin, essaie le perl.
T'es pas obligé de devenir un pro du perl pour l'utiliser ;)
[^] # Re: Perl..? :-s
Posté par Spack . Évalué à 1.
C'est justement mon cas ;-) et en plus ça concerne principalement du traitement de texte...
Je vais voir de plus près à quoi ressemble Perl en espérant tomber sur un tutoriel plus simple à comprendre que l'article de Wikipédia...
[^] # Re: Perl..? :-s
Posté par briaeros007 . Évalué à 2.
perl
my $nom_variable; #on crée une variable
tableau @nom_tableau=(element1,element2);#on crée un tableau et on met 2 element dedans
for my $val (@nom_tableau)
{
print "Ma valeur est $val";#on affiche la valeur de chaque élément du tableau)
}
#!/usr/bin/perl
my $toto="abc";
my $titi=1;
my @tab;
$titi+=1;
if ($titi==1)
{
push(@tab,"titi vaut 1");
}
elsif ($titi==2)
{
push(@tab,"titi vaut 2");
}
else
{
push (@tab,"toto");
}
for my $tata (@tab)
{
if ($tata=~ m/vaut [0-9]/)
{
print "tata contient la phrase \"vaut <un chiffre>\"";
}
}
[^] # Re: Perl..? :-s
Posté par Ontologia (site web personnel) . Évalué à 3.
J'utilise que des foreach sur les liste/hash, bon d'accord, quelques map de temps en temps...
Je n'utilise que des if ( $toto =~ /truc/) avec capture ou d'autres if qui ressemblent à ce qu'on trouve en php/C (tests sur chaines et entier).
Bref, on peut faire du perl propre et clair.
J'écris jamais ce genre de code : http://shootout.alioth.debian.org/gp4/benchmark.php?test=knu(...) parce que j'y comprend rien, et je ne suis surement pas le seul.
En fait j'écris du perl comme un type qui a fait du basic de 7 ans à 12 ans, du pascal de 15 à 20 et de l'objet après. Donc ça reste clair ;)
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: Perl..? :-s
Posté par Sytoka Modon (site web personnel) . Évalué à 1.
Sinon, comme je l'ai dis dans un autre post, je me suis mis a essayer Erlang et il y a des concepts vraiment intéressants à reprendre même si je ne suis pas sur que cela soit facile de placer cela dans un langage procédural. En fait, Erlang, c'est presque le symétrique du Fortran ;-)
[^] # Re: Perl..? :-s
Posté par Ontologia (site web personnel) . Évalué à 2.
Avec COP, et une granulité moins fine, on devrait pouvoir implémenter ce genre de chose avec des objets générique, le containeur s'occupant de boucler et gérer les yields.
Bon après dans la pratique je sais pas ce que ça va donner, COP est encore un concept théorique.
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: Perl..? :-s
Posté par Sytoka Modon (site web personnel) . Évalué à 2.
Je ne me souviens plus exactement mais COP, c'est le truc de Meyer pour faire du parallèle ? Je suis surpris si c'est cela que ce modèle soi disant génial (je suis incapable de juger s'il est bien ou non dans l'absolu, pas assez de recul la dessus) ne soit toujours pas implémenté.
Je pense que les langages qui font tout pour favoriser un parallélisme simple et qui marche seront de plus en plus utilisé dans le futur. Avec l'augmentation du nombre de coeur, il faut clairement un langage parallèle dans son âme (un peu comme Erlang). C'est d'ailleurs ce qui m'inquiète avec Perl6 car j'aime beaucoup Perl et je n'ai pas l'impression que l'aspect parallèlisation ait été au coeur de la conception du nouveau langage.
[^] # Re: Perl..? :-s
Posté par Ontologia (site web personnel) . Évalué à 2.
Dans le C généré, il y a des goto, parce que dans certains cas c'est plus rapide ou impossible de faire autrement (certaines dérécurcivations).
Le modèle de Meyer est SCOOP, il consiste à ajouter un mot clé devant la déclaration d'une variable.
COP est adapté au prototypes, qui nécessitent de s'adapter, car la logique diffère un peu (en gros, en quelques sortes, le paradigme à classe est un sous ensemble du paradigme à prototype, donc SCOOP fit pas tout l'ensemble).
COP est en cours d'implémentation, ça prend du temps et l'implémenteur a des cours à donner, des mémoires de maitrises à superviser, des publis à écrire, etc...
Les débuts d"implémentation indiquent bien que ça permet de paralléliser proprement et très simplement : tu créés plein d'objets, tu lances et il se débrouille assez bien, ie. ça se répartie bien sur les coeurs.
Quand ça sera prêt et nickel on le publiera (enfin en tout cas, je défend pour ma part l'idée - au sein du projet - que je préfère que ça sorte avec 6 mois de retard mais que ce soit nickel).
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: Perl..? :-s
Posté par Sytoka Modon (site web personnel) . Évalué à 2.
Sinon, en gros, si je comprends bien COP, c'est un peu SCOOP mais adapté au concept de la programmation par prototype. C'est génial lorsque cela marchera car après avoir lu Meyer, on était vachement frustré de ne pouvoir essayer pour de vrai.
Sinon, je te conseille de regarder du coté d'Erlang pour la gestion des erreurs. C'est très intéressant et vraiment différents de ce que font les autres et en plus dans une philosophie multi-coeur. Avec ton COP, cela pouvoir s'intégrer vu le peu que je devine.
Ensuite, question timing... On est tous un peu surchargé et c'est pas la tendance ministerielle actuelle qui va changer la donne ;-( C'est dommage qu'il n'y ai pas plus de moyen humains sur ce projet.
[^] # Re: Perl..? :-s
Posté par arthurwolf . Évalué à 0.
Si tu sais coder en PHP, tu sais coder en Perl.
C'est pas plus dur que ca.
Et par dessus ca, tu as 9 tonnes de creme chantilly, des tonnes de petits trucs à apprendre/comprendre qui te rendent plus rapide, ton code plus beau, plus puissant ... mais t'es pas obligé, et tu peux les apprendre à ton rythme.
Et le CPAN.
Et Perl6.
Perl, c'est trop bien.
[^] # Re: Perl..? :-s
Posté par Spack . Évalué à 2.
Et une fois que l'on a les bases, on s'aperçoit que l'on peut rapidement et très simplement faire des choses assez puissantes. Il y a un grand nombre de modules disponibles. Les règles implicites du langage assurent une certaine rapidité lors de l'écriture d'un script mais il ne faut pas trop en abuser.
Bref je ne regrette pas d'avoir dépasser mes appréhensions et Perl est maintenant un bon compagnon :)
# Polymorphisme
Posté par Aissen . Évalué à 3.
http://mauke.ath.cx/stuff/poly.html
Ce script fait un hello world en Perl(6), Ruby, Python, bash, zsh, js, html, C, C++, haskell… Au total une vingtaine de langages et variantes dans le même fichier. C’est assez instructif!
[^] # Re: Polymorphisme
Posté par jiyuu . Évalué à 1.
D'ailleurs c'est marrant de constater que la partie 'ruby' et la même que la partie 'perl'. La différence se fait sur la valeur booléenne du nombre 0.
Je savais que le concepteur du langage ruby c'était inspiré entre autre de perl mais je ne pensais pas que c'était à ce point... :)
# Python c'est super !
Posté par Victor STINNER (site web personnel) . Évalué à 6.
Pour les expressions régulières : tout est objet en Python, donc une expression régulière est un objet et un « match » est aussi un objet. Voir la doc :
http://docs.python.org/library/re.html#regular-expression-ob(...)
La méthode .sub() (« replace all ») accepter une chaîne ou une fonction pour le remplacement. Exemple : re.sub("([0-9a-f]+)", lambda regs: str(int(regs.group(1), 16)), texte, re.IGNORECASE) convertit les nombres hexadécimaux en décimal ("x=10" donne "x=16"). On peut extraire la lambda fonction (et la définir avant) pour une meilleure lisibilité.
Pour les traitements sur les ensembles (et non pas uniquement sur les tables de hash ou listes), Python implémente les itérateurs de manière très générique : « for x in data: ... » équivaut à :
gen = iter(data)
while True:
x = gen.next()
...
Les types de base (dict, list, tuple) implémentent cette API. Mais de nombreux objets l'implémentent également : fichier (lecture ligne par ligne), résultat d'une base de donnée, document XML, etc.
À partir de ça, on peut créer des expressions de type : « results = [(x * 10) for x in data if (x % 3) == 2] ». C'est la forme abrégée de
results = filter(lambda x: (x % 3) == 2, donnees)
ou encoreresults = map(lambda x: x*10, donnees)
results = []
for x in donnees:
if (x % 3) == 2:
results.append(x * 10)
Je trouve cette programmation, inspirée des langages fonctionnels, élégante. Bien qu'utilisé abusivement, elle peut rendre le code difficile à relire.
Je ne connais pas bien Perl, mais je pense que « @liste = %h{@t}; » s'écrit « liste = [h[cle] for cle in t] » en Python. C'est plus verbeux, mais se comprend plus facilement (pas besoin de connaître le sens des préfixes @ et $).
Au sujet des appels de fonction. En PHP, les objets passés en paramètres sont passés par copie. C'est assez pénible, il faut écrire explicitement &$object pour le passer par référence. Ceci peut être fait dans le prototype de la fonction... ou lorsqu'on l'appelle. S'en suit un gros merdier au niveau des effets de bord. En Python, tous les objets sont passés par références (et tout est objet), sauf que certains objets sont immutables (non modifiables) comme les tuples, les nombres entiers et les chaînes de caractères.
Pour l'assignation, pareil : c'est une copie de référence et non pas copie de l'objet : a=b fait que a et b pointent sur la même donnée. Par contre, lorsqu'on modifie a, b va être modifié ou non selon la même règle qu'avant :
- type mutable : a et b sont modifiés
- type immutable : a forke et crée un nouvel objet
En gros, Python est un pot pourri de divers langages (un peu de Perl par ci, un peu de Lisp par là, un peu de Java, etc.) mais qui en a extrait le meilleur pour donner un langage homogène et très souple.
[^] # Re: Python c'est super !
Posté par Jean B . Évalué à 2.
[^] # Re: Python c'est super !
Posté par benoar . Évalué à 2.
[^] # Re: Python c'est super !
Posté par windu.2b . Évalué à 5.
1 http://fr.wiktionary.org/wiki/immuable
2 http://en.wiktionary.org/wiki/immutable
# Mes 2 cents
Posté par matli . Évalué à 5.
L'une des premières raison est que quelque soit l'Unix sur lequel je travaille, je suis quasiment sûr d'avoir un Perl installé, c'est beaucoup moins sûr avec les autres langages cités dans ce journal.
Une autre raison est que ce langage correspond parfaitement à mon besoin: analyse de texte, migration de données, manipulation de fichiers,... Je n'ai jamais été confronté à une limitation de ce langage qui m'aurait obligé à utiliser autre chose. Au passage, je me permets également de souligner les performances de Perl pour les traitement sur les fichiers, ça compte quand comme moi on joue avec des fichiers de log compressés de plusieurs Giga. Sur ce terrain là, Python, Ruby and co sont encore loin.
Je ne l'utilise que de façon simple, comme beaucoup de personnes l'ont signalé ici. Les trucs implicites, oui un peu, mais pas trop.
@liste = %h{@t};
je n'aime pas trop par exemple. De même, quand je lis un fichier, je préfère un truc du genre
while (my $line=<IN>)
que
while (<IN>)
Je pense que le procès d'illisibilité est un faux procès, dans n'importe quel langage on peut écrire des choses illisibles. Il est tout à fait possible avec un peu de discipline de faire un code lisible. Voire par exemple les Best practices de Damian Conway.
Il y a bien sûr le CPAN, avec son installeur de module en ligne de commande qui résout les dépendances:
perl -MCPAN -e shell
cpan shell -- CPAN exploration and modules installation (v1.7602)
ReadLine support enabled
cpan> install mon_module
...
Tous les modules nécessaires sont téléchargés et installés, comme apt-get ou yum
Pour le Web, il y a des frameworks assez complets comme Catalyst ou Mason. Pour ma part, je reste simple avec CGI::Application associé au Template toolkit. C'est propre et simple.
Et puis, il y a mod_perl, c'est à dire l'intégration de Perl dans Apache, et là, ça déchire vraiment.
Bref, Perl et moi, ça risque de continuer encore un moment. Je n'ai pas d'impatience particulière vis à vis de Perl6. La seule chose qui m'ennuie un peu dans Perl5, c'est que l'on soit obligé d'implémenter les objets avec des Hash (ou avec une structure "physique" définie), alors que c'est en général opaque dans les autres langages et ça le sera dans Perl6.
# A propos de liste et de hash
Posté par Philippe F (site web personnel) . Évalué à 1.
La syntaxe est la même :
mydict[ mykey ] = myvalue
bien sur, mykey et myvalue peuvent être de type quelconques, un dictionnaire peut stocker un peu n'importe quoi et la clé doit juste être hashable.
Lua optimise le choix entre liste et dictionnaire en fonction de la taille de l'ensemble et de la présence de clusters de clés.
Je ne me souviens plus de l'algo, mais une implémentation naive pourrait être :
- moins de 10 élements, pas besoin de hash, on fait des listes chaînées et des comparaison de clé direct
- plus de 10 éléments, moins de 30 éléments mais cluster de clé sous forme d'entiers à valeur proche, on garde une liste chaînée
- tout le reste, on fait des hash avec des dictionnaires
Bien sur, l'implémentaiton est plus subtile que ça et optimisée pour des cas réels.
Au début, j'avais trouvé ça étrange mais en y réfléchissant, je trouve ça plutot sympa. Dans les faits, il y a très peu de différences entre une liste de 3 éléments et un dictionnaire de 3 éléments.
Si tu réfléchis au hash pour lisaac, il y a peut-être des choses à aller chercher là dedans.
[^] # Re: A propos de liste et de hash
Posté par Ontologia (site web personnel) . Évalué à 3.
Un tableau, un hash, ce sont deux ensembles E et F et une fonction f : E -> F où tablo[val] ∈ F et val ∈ E, avec f(val) = tablo[val].
Que E soit un sous ensemble de |N ou n'importe quoi, le concept est le même, d'où la possibilité d'indifférencier tableau et hash.
Historiquement il y a une différence pour des questions de perfs et de hauteur de niveau du langage, mais potentiellement avec un compilateur intelligent, il y a maintenant moyen de pallier facilement à cela...
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
# foo
Posté par gc (site web personnel) . Évalué à 3.
tu devrais regarder Prolog, c'est exactement ça.
# suite
Posté par TImaniac (site web personnel) . Évalué à 2.
[^] # Re: suite
Posté par Ontologia (site web personnel) . Évalué à 2.
Cela dit C#3 a un concept très intéressant, qui m'a l'air pas trop mal implémenté : l'espèce de SQL intégré (LINQ) dont je me servirais abondamment s'il existait en java.
Pour le reste, C# est un clone de java et ça c'est vraiment l'horreur.
D'ailleurs, je me demande si les compréhensions de listes de Python permettent de faire ce que permet LINQ
( http://en.wikipedia.org/wiki/Language_Integrated_Query )
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: suite
Posté par Jean B . Évalué à 2.
Yes they can !
-->[]
Plus sérieusement oui, même si la syntaxe sera bien plus éloignée du SQL.
Mais vu qu'on peut faire des SELECT avec for, des FROM avec in, des JOIN avec +, des WHERE avec if, etc.
On peut même le faire en évaluation paresseuse avec les moins connues genexp.
[^] # Re: suite
Posté par Sytoka Modon (site web personnel) . Évalué à 1.
Inline::Java
Inline::Python
Inline::Ruby
....
Je n'ai jamais utilisé en pratique mais c'est bien dans la philosphie Perl de mettre de la glue dans tous les sens.
[^] # Re: suite
Posté par briaeros007 . Évalué à 2.
Quant au inline, si tu savais ce qu'on peut faire en c/c++ (des trampolines par exemples) XD!
[^] # Re: suite
Posté par Nicolas Boulay (site web personnel) . Évalué à 2.
"La première sécurité est la liberté"
[^] # Re: suite
Posté par TImaniac (site web personnel) . Évalué à 2.
- passage de paramètres par références
- expressions lambda
- inférence de type
- gestion des pointeurs
- pointeur de méthodes (délégués)
- méthodes d'extensions
- coroutine
- types anonymes
Au final, LINQ n'est qu'une bibliothèque pas spécifique à C# et utilisable dans d'autres langages. C# ajoute juste un peu de sucre syntaxique au dessus de LINQ.
[^] # Re: suite
Posté par Ontologia (site web personnel) . Évalué à 2.
Toutes ces features sont très bien (sauf la gestion de pointeur, je veux plus entendre parler de pointeur), mais je les retrouves dans les langages que j'aime : Lisaac, Perl, Caml.
Et plutôt que des délégués, je préferai un bon type Block.
C'est LINQ qui m'intéresse beaucoup, et qu'il va falloir que je regarde de près, car nous avons le projet de permettre ça dans Lisaac (dans les 2 ans à venir). Il faut donc réfléchir à la syntaxe, est-elle assez simple, comment peut elle s'intégrer avec le langage, peut-on "tout faire" avec, etc...
Faut reconnaitre que krosoft a fait du très bon boulot avec LINQ. Pour une fois qu'ils ont inventé quelques chose eux-même...
« Il n’y a pas de choix démocratiques contre les Traités européens » - Jean-Claude Junker
[^] # Re: suite
Posté par TImaniac (site web personnel) . Évalué à 2.
[^] # Re: suite
Posté par el_mickey . Évalué à 1.
Mais bon c'est le c#, compromis sur compromis. Donc c'est sympa tu as un peu de tout, ça reste utilisable mais quelque fois tu aimerais pouvoir aller un peu plus loin.
[^] # Re: suite
Posté par TImaniac (site web personnel) . Évalué à 2.
[^] # Re: suite
Posté par TImaniac (site web personnel) . Évalué à 3.
maLib.Do(
() => whatyouwanthere()
)
.While(
() => a != b
)
On s'éloigne de la syntaxe C que tu détestes :)
Pareil avec LINQ, on est vraiment loin de ce qu'on lit en C habituellement :
http://blogs.msdn.com/lukeh/archive/2007/10/01/taking-linq-t(...)
[^] # Re: suite
Posté par Antoine . Évalué à 2.
Ca dépend du sens exact de la question. En tout cas ça ne permet pas de s'interfacer avec une base SQL, ça ne travaille que sur le type liste natif.
# haskell
Posté par TeXitoi (site web personnel) . Évalué à 5.
Dans tous les langages que je connais, y compris OCaml, si le message/fonction n'existe pas pour le type, le compilateur répond qu'il ne sait pas quoi faire.
Je n'ai jamais vu le pattern de raisonnement mafonction : ELEMENT1 -> ELEMENT2 => mafonction : COLLECTION[ELEMENT1] : COLLECTION[ELEMENT2].
tu veux dire un map généralisé? en haskell, c'est vraiment tout simple :
Prelude> let f x = x + 1
Prelude> fmap f [1,2,3]
[2,3,4]
Prelude> fmap f (Just 5)
Just 6
Prelude> :t fmap
fmap :: (Functor f) => (a -> b) -> f a -> f b
En gros, ca veux dire que si tu veux que ton type fasse partie du typeclass Functor, tu dois implémenter fmap. Ensuite, fmap s'applique sur toute valeur dont le type fait partie de la typeclass Functor. Ici, les types liste et Maybe (équivalent de l'option en OCaml, un résultat ou pas de résultat).
Beaucoup de types font partie de cette typeclass (et aussi la typeclass monad, mais ca devient un poil plus compliqué). Tu peux bien sur faire de même pour tes nouveau types.
[^] # Re: haskell
Posté par Thomas Douillard . Évalué à 5.
Il y a pas à dire, c'est beau la rencontre des maths et de l'informatique.
Le foncteur, c'est comme une fonction, mais généralisé sur un ensemble de domaine et de résultat différent, et qui mappe des fonction à d'autre fonction au lieux de mapper d'un ensemble A -> B ... et c'est un concept de theorie_des_categories
Genre ça mappe n'importe quelle fonction f A->B a une fonction collection(F) : collection(A) -> collection(B) dans notre exemple.
Suivre le flux des commentaires
Note : les commentaires appartiennent à celles et ceux qui les ont postés. Nous n’en sommes pas responsables.