270

Zeph (./267) :
Moi je le trouve au contraire plutôt très bien foutu, malgré son age il continue à être largement utilisable aujourd'hui et à accueillir des concepts "modernes" (enfin pas tant que ça, mais disons qu'ils deviennent grand public aujourd'hui) de façon assez naturelle. Il suffit par exemple de jeter un coup d'oeil à ce qui se fait au niveau programmation asynchrone, à l'heure où .NET ne sait pas sur quel pied danser d'une version à l'autre et Java se traine des implémentations pétées au point d'envisager de piquer toutes celles de Scala. Alors qu'en JS on a jQuery qui propose des futures/promises très élégantes depuis un bon moment smile

J'ai regardé deux ou trois tutos pour comprendre les bases du JS. À chaque fois, ils commencent par dire que c'est un modèle objet par prototypes, que c'est fantastique et bien mieux que les modèles par classes. Et l'étape suivante, c'est comment implémenter un système de classes, parce que c'est quand même vachement plus pratique tritop
Sans compter le == dont il ne faut surtout pas se servir (mais pourquoi l'avoir mis, alors ?), l'absence de hashmap utilisables (enfin, tu as le object, mais dès que tu fais une boucle sur les clefs, il faut faire du filtrage pour supprimer les clefs indésirables — et il faut donc pouvoir faire la distinction tritop), l'utilisation périlleuse de this, …
avatar
<<< Kernel Extremis©®™ >>> et Inventeur de la différence administratif/judiciaire ! (©Yoshi Noir)

<Vertyos> un poil plus mais elle suce bien quand même la mienne ^^
<Sabrina`> tinkiete flan c juste qu'ils sont jaloux que je te trouve aussi appétissant

271

Zeph (./269) :
P.S. : pour ton anecdote, c'est pas la première fois : Firefox n'utilisait par défaut pas les réglages internet de Windows pour aller sur internet, et encore aujourd'hui il embarque son propre cache DNS ^^

Firefox a également du mal avec l'intégration sur OS X: proxy, correcteur orthographique/grammatical, certificats, gestion des mots de passe, clefs privées, …

Sur Linux, on peut gérer presque proprement les certificats, il faut simplement recompiler la libnss (quelle bonne idée de mettre ça en dur dans le code \o/)
avatar
<<< Kernel Extremis©®™ >>> et Inventeur de la différence administratif/judiciaire ! (©Yoshi Noir)

<Vertyos> un poil plus mais elle suce bien quand même la mienne ^^
<Sabrina`> tinkiete flan c juste qu'ils sont jaloux que je te trouve aussi appétissant

272

./270 : pour "==", je suis entièrement d'accord, c'est de la merde tout autant qu'en PHP et ça n'aurait jamais du exister. Il faut accepter le fait que tant pis, cet opérateur doit toujours s'écrire "===", c'est moche mais c'est pas (trop) compliqué à contourner.

Pour le reste, je n'y peux rien si tu tombes sur des tutos écris par des gens qui ne savent pas s'ils veulent des classes ou non grin Je trouve que c'est assez puissant de pouvoir implémenter aussi facilement les classes et l'héritage dans un langage, mais en pratique ça n'est utile que si on veut vraiment faire de la POO dans un gros framework. Enfin, pour les hashmaps, les objects en sont et il n'y a aucun filtrage à faire ? Le filtrage c'est uniquement si tu utilises un tableau comme une hashmap puisqu'effectivement tu te prends les propriétés du tableau en plus de tes clés quand tu itères dessus. Mais un tableau n'est pas fait pour être utilisé comme une hashmap, donc c'est normal que ce soit bancal ^^

À mon avis une bonne partie de ces confusions viennent du fait qu'on regarde JavaScript avec un a priori "objet", or ce n'est pas du tout un langage objet. Du coup on essaie de réimplémenter les objets pour se mettre en terrain connu, on s'étonne du fait que le mot-clé "this" ne fasse pas la même chose que dans des langages objets, etc. Pourtant ces concepts ne sont pas plus ou moins logiques, à condition de ne pas les appréhender en ayant trop d'idées déjà faites à propos de ce que "devrait" faire this, ce que "devrait" supporter switch comme syntaxe ou ce que "devrait" faire un tableau quand on examine ses propriétés.
avatar
All right. Keep doing whatever it is you think you're doing.
------------------------------------------
Besoin d'aide sur le site ? Essayez par ici :)

273

./258 : Dans pas mal de langage comme le Java ça serait refusé. Comme le dit Orion_ une série de if serait tout aussi claire mais au moins ce code reste tout a fait compréhensible et sans surprise contrairement a énormément de chose possible en JavaScript qui reste un des meilleurs langages pour se tirer une balle dans le pied après le C++.
Zeph (./267) :
Moi je le trouve au contraire plutôt très bien foutu, malgré son age il continue à être largement utilisable aujourd'hui et à accueillir des concepts "modernes" (enfin pas tant que ça, mais disons qu'ils deviennent grand public aujourd'hui) de façon assez naturelle.
Comme le PHP ou le BASIC, c'est surtout un langage à la base bricolé qu'on a essayé de faire évoluer tant bien que mal vers plus de professionnalisme, mais qui se traîne un lourd héritage dans sa syntaxe de base, le pire étant certainement les conversions qui sont un énorme piège.

De plus on essaie de plus en plus souvent de l'utiliser pour des usages ou il n'est clairement pas vraiment adapté comme d'énorme base de codes avec de gros besoins de performances.
Son gros avantage c'est sa souplesse qui en fait un bon langage de script, certainement pas la rigueur et les performances.
avatar

274

Zeph: non ECMAScript est apparu apres Javascript.
Brendan Eich a initialement développé un langage de script côté serveur, appelé LiveScript, pour renforcer l'offre commerciale de serveur HTTP de Mosaic Communications Corporation. La sortie de LiveScript intervient à l'époque où le NCSA force Mosaic Communications Corporation à changer de nom pour devenir Netscape Communications Corporation.
Netscape travaille alors au développement d'une version orientée client de LiveScript. Quelques jours avant sa sortie, Netscape change le nom de LiveScript pour JavaScript. Sun Microsystems et Netscape étaient partenaires, et la machine virtuelle Java de plus en plus populaire. Ce changement de nom servait les intérêts des deux sociétés.

Netscape soumet alors JavaScript à Ecma International pour standardisation. Les travaux débutent en novembre 1996, et se terminent en juin 1997 par l'adoption du nouveau standard ECMAScript. Les spécifications sont rédigées dans le document Standard ECMA-262.
avatar
Proud to be CAKE©®™


GCC4TI importe qui a problème en Autriche, pour l'UE plus et une encore de correspours nucléaire, ce n'est pas ytre d'instérier. L'état très même contraire, toujours reconstruire un pouvoir une choyer d'aucrée de compris le plus mite de genre, ce n'est pas moins)
Stalin est l'élection de la langie.

275

GoldenCrystal (./268) :
(Et parlons donc du fonctionnement des proxy d'entreprise avec nodejs ou atom... De la grosse daube, ça marche juste pas tritop. C'est la première fois que je vois des mec arriver à pondre une version Windows d'un outil qui par défaut n'utilise pas les réglages Internet pour aller sur internet triso Je vous souhaite de ne jamais vivre ça…)
Les proxy ca a toujours été un bordel, vu que pendant longtemps ils n'était pas ou mal gérés pas le système, beaucoup d'applications utilisent leur propres réglages, node.js est très loin d'être la seule application dans ce cas.
avatar

276

Zeph (./259) :
par contre comment t'es tombé là-dessus ? biggrin.gif
(c'était un lien sur TheDailyWTF ^^)
avatar
Zeroblog

« Tout homme porte sur l'épaule gauche un singe et, sur l'épaule droite, un perroquet. » — Jean Cocteau
« Moi je cherche plus de logique non plus. C'est surement pour cela que j'apprécie les Ataris, ils sont aussi logiques que moi ! » — GT Turbo

277

./273 : précisément, c'est parce que cette intention est mal comprise que JavaScript est détourné de son but premier pour faire des applications qui ont besoin de perf, des clients lourds, des choses côté serveur et autres cas d'utilisation pour lesquels il n'est pas adapté.

./274 : je n'ai pas dit qu'il était apparu avant ou après, je répondais juste à ton post : JavaScript (sous cette appellation) a été prévu initialement pour tourner côté client, c'est d'ailleurs écrit noir sur blanc dans ta citation ^^
avatar
All right. Keep doing whatever it is you think you're doing.
------------------------------------------
Besoin d'aide sur le site ? Essayez par ici :)

278

Zeph (./272) :
pour "==", je suis entièrement d'accord, c'est de la merde tout autant qu'en PHP et ça n'aurait jamais du exister.

#pascrayon# Je me sers souvent de empty() en PHP. Je sais dans quel contexte je l'utilise, pas besoin d'écrire un long if ($x || (is_null($x) || ($x === '') || ...). En fait paradoxalement, autant je suis très ferme sur la structure de mes bases en SQL, autant en PHP j'aime bien que ($i == 1) et ($i == '1') aient le même résultat, et que je choisisse de moi même si je veux un type strict avec ===. Je pense que ce que certains voient comme un laisser-aller ou une aberration, je le vois comme une liberté où je ne vais pas avoir (la plupart du temps) à passer par un cast ou un autre type de transtypage pour des variables qui, humainement parlant, véhicule la même information désirée. Et PHP n'est pas le langage le plus souple à ce sujet.
avatar
« Nous avons propagé sur Extranet une histoire fabriquée de toutes pièces selon laquelle une certaine disposition d'étoiles, vue depuis la planète d'origine des butariens, formaient le visage d'une déesse galarienne.
Sans chercher à vérifier ces informations, certains ont décrété que c'était la preuve de l'existence de la déesse. Ceux qui notaient le manque de preuves se faisaient attaquer. »

Legion, geth trolleur à portée galactique

279

Zeph (./272) :
Pour le reste, je n'y peux rien si tu tombes sur des tutos écris par des gens qui ne savent pas s'ils veulent des classes ou non grin Je trouve que c'est assez puissant de pouvoir implémenter aussi facilement les classes et l'héritage dans un langage, mais en pratique ça n'est utile que si on veut vraiment faire de la POO dans un gros framework.

Je n'ai toujours pas vu l'intérêt du système par prototypes, à vrai dire grin
Enfin, pour les hashmaps, les objects en sont et il n'y a aucun filtrage à faire ?

Tu devrais jouer avec ExtJS ^^ Tes objects vont se retrouver avec des propriétés inconnues.
D'ailleurs, je bosse sur un petit projet actuellement que j'ai décidé de faire proprement, donc en activant les warning (JSHint/JSLint). Il râle à chaque boucle for
key in my_hashmap
en disant que je dois filtrer les propriétés pour ne garder que celles intéressantes tritop
À mon avis une bonne partie de ces confusions viennent du fait qu'on regarde JavaScript avec un a priori "objet", or ce n'est pas du tout un langage objet. Du coup on essaie de réimplémenter les objets pour se mettre en terrain connu, on s'étonne du fait que le mot-clé "this" ne fasse pas la même chose que dans des langages objets, etc. Pourtant ces concepts ne sont pas plus ou moins logiques, à condition de ne pas les appréhender en ayant trop d'idées déjà faites à propos de ce que "devrait" faire this, ce que "devrait" supporter switch comme syntaxe ou ce que "devrait" faire un tableau quand on examine ses propriétés.

En pratique, je suis quand même tout le temps obligé d'utiliser des fonctions anonymes pour des trucs vraiment bêtes, simplement à cause de ça sad

Accessoirement, je n'aime pas les langages dont les opérations de base ne respectent pas les propriétés classiques (genre la commutativité de l'addition, que la soustraction ne soit pas l'inverse de l'addition, …).
avatar
<<< Kernel Extremis©®™ >>> et Inventeur de la différence administratif/judiciaire ! (©Yoshi Noir)

<Vertyos> un poil plus mais elle suce bien quand même la mienne ^^
<Sabrina`> tinkiete flan c juste qu'ils sont jaloux que je te trouve aussi appétissant

280

Zeph (./269) :
Pour .NET c'est un peu n'importe quoi. Ils ont commencé à mettre des callbacks partout, sauf qu'ils ne savaient pas trop comment faire entrer synchrone et asynchrone dans les mêmes APIs du coup on a des "IAsyncResult" qui ne ressemblent à rien avec une douzaine de propriétés pour savoir si un truc a été fini de façon synchrone, s'il a été lancé, s'il tourne toujours, s'il faut l'attendre ou s'il va nous rappeler quand il aura fini.
Ouais, c'est le Modèle asynchrone « préhistorique », il était chiant à utiliser et pas joli, mais il fonctionnait très bien, moyennant ses défauts (pollution du heap)
Ensuite on a eu les Task, sauf qu'ils ont voulu comme d'habitude être compatibles avec tout l'historique donc c'est pareil : on a des Task qui sont à la fois des futures, des promises, des machins qui ressemblent à des WaitHandle sur lesquels on peut faire "Wait()" et tout un tas d'autres méthodes obscures.
Heu ouais, mais à te lire j'ai presque l'impression que tu tu reproches au truc d'être un couteau suisse fonctionnel plutôt qu'un couteau de cantine qui ne coupe pas tongue
Sachant qu'on est en environnement .NET, l'intérêt principal de la chose est que ça s'intègre parfaitement avec le reste.
Certes, Task implémente IAsyncResult, mais a ne mange pas de pain, et si tu ne le sais pas, tu ne le vois pas. (C'est utile, ça t'évite d'implémenter un IAsyncResult toi-même… Cela dit je peux concevoir que ce soit un aspect de Task peut reluisant, n'étant pas moi-même très fan des IAsyncResult)
Ensuite, Task représente comme son nom l'indique une tâche (avec ou sans résultat), c'est à dire un truc qui se passe ailleurs. T'as effectivement deux types de tâches, un qui représente l'exécution de code sur un thread quelconque, et un qui représente juste l'état d'opération d'une opération. Au final, quel que soit l'origine de ta tâche, c'est transparent pour l'utilisateur de l'objet, ce qui est l'intérêt principal de la chose. (Et c'est pas parce que ça piétine allègrement les frontières de classification de certains que ça veut dire que c'est mal fichu…)
Ensuite, ta tâche implémente Wait… Ouais, ça semble un gros défaut comme ça… Sauf qu'en réalité, c'est quand même occasionnellement bien pratique. Notamment le fait qu'un appel de .Wait() (ou de .Result equivalent, le cas échéant) exécute automatiquement la tâche en mode synchrone lorsque c'est possible. (Oui, ça a l'air vraiment couillon, mais y'a des cas où c'est (très)pratique.)
Le fait que la tâche fournisse un WaitHandle (optionnel), c'est inévitable. Task, c'est quand même « un peu » l'équivalent d'un ManualResetEvent, et ce serait vraiment mal vu de ne pas fournir cette aide. (D'autant qu'un WaitHandle est un objet système, donc inter-opérable avec beaucoup de choses…)
Ne pas oublier: Multithread vs Monothread… sorry
En fait, tu peux faire à peu près tout ce que tu veux niveau signalisation asynchrone avec les tâches, et c'est vraiment très pratique. (Je te suggère la série des Async Coordination Primitives si tu ne l'as pas lue)
Je suis désolé mais en regardant l'API de "Task" je trouve qu'il faudrait être de sacrément mauvaise fois pour prétendre que c'est bien pensé ou élégant grin
Y'a franchement pas énormément de méthode. Vu le peu qu'il y a de disponible (hors surcharges) je trouve ça d'assez mauvaise foi de dire que ce soit vraiment mal pensé… tongue (J'ai franchement vraiment l'impression que tu reproches au truc d'être flexible et interopérable…)
Perso si je devais reprocher un seul truc c'est Task.Factory… Je hais les « Factory » du plus profond de mon être.
P.S. : pour ton anecdote, c'est pas la première fois : Firefox n'utilisait par défaut pas les réglages internet de Windows pour aller sur internet, et encore aujourd'hui il embarque son propre cache DNS ^^
Oui, maintenant que tu le dis… M'enfin c'est juste du gros foutage de gueule quoi :/
Enfin autant Firefox, à l'époque d'IE6, où les entreprises étaient on-ne-peut-plus strictes sur la politique d'installation de navigateurs Web, c'était moins dérangeant, autant quand t'es développeur et que tu peux pas utiliser un putain d'outil de dev. sur ton poste sans faire des contorsions de malade, c'est absolument ridicule…
(Lancer une « application » avec un fichier .bat ? Mettre mon mot de passe en clair dans un fichier .bat ? Oui mais bien sûr… Bienvenue dans le monde des cavernes, la sécurité se trouve au fond de mon cul…)

./275 > Mais Node.js / Atom sont modernes… :/
flanker (./279) :
Tu devrais jouer avec ExtJS ^^
ExtJS… sick
avatar
Le scénario de notre univers a été rédigée par un bataillon de singes savants. Tout s'explique enfin.
T'as un problème ? Tu veux un bonbon ?
[CrystalMPQ] C# MPQ Library/Tools - [CrystalBoy] C# GB Emulator - [Monoxide] C# OSX library - M68k Opcodes

281

Je sais bien que les Tasks ne proposent pas de choses complètement inutiles, forcément si tu regardes les fonctionnalités séparément une à une elles ont du sens. Ce que je leur reproche, c'est de proposer tout *à la fois*, c'est à dire d'être un mélange d'à peu près tous les paradigmes asynchrones qui existent. Si je veux fournir une API asynchrone dans laquelle je ne veux pas exposer de "Wait()" (parce que je considère que ça serait un risque de bloquer un thread pour tel ou tel évènement), je ne vais pas pouvoir utiliser Task. Je suis assez d'accord avec ce que raconte ce mec sur la séparation claire des APIs synchrones et asynchrones, donc un petit lien plutôt que de tout recopier ici : http://blog.ometer.com/2011/07/24/callbacks-synchronous-and-asynchronous/

./279 : les prototypes sont là pour fournir un mécanisme d'extension d'objets, ça peut être utile dans des gros frameworks (beaucoup les utilisent d'ailleurs). On pourrait se poser exactement la même question pour les langages objets, ça n'est pas toujours utile, et il vaudrait mieux parfois s'en passer plutôt que de se forcer à les utiliser en faisant n'importe quoi. Par ailleurs le fait qu'ExtJS soit remplie de mauvaises idées ne prouve pas forcément que JavaScript est plein de défauts grin

À propos de JSLint je sais qu'il râle à cause de ça, et justement parce que beaucoup de devs faisaient des "for (var key in my_array)" en s'imaginant que ça allait sortir la liste des indices. Maintenant que tu es un développeur éclairé par cette connaissance, je t'encourage à désactiver ce warning parce que tu sais ce que tu fais et que ton utilisation du "for (var key in my_object)" est tout à fait fiable et légitime hehe

Sinon pour les opérateurs, je suis d'accord et la raison cachée derrière est la même que pour l'opérateur "==" : c'est une histoire de casts implicites qui pourrit beaucoup le langage. En supprimant cette règle on corrigerait je pense un bon paquet des défauts de JavaScript, mais comme pour PHP ça n'arrivera jamais à cause de la rupture complète de compatibilité que ça causerait sad
avatar
All right. Keep doing whatever it is you think you're doing.
------------------------------------------
Besoin d'aide sur le site ? Essayez par ici :)

282

Zeph (./281) :
Je sais bien que les Tasks ne proposent pas de choses complètement inutiles, forcément si tu regardes les fonctionnalités séparément une à une elles ont du sens. Ce que je leur reproche, c'est de proposer tout *à la fois*, c'est à dire d'être un mélange d'à peu près tous les paradigmes asynchrones qui existent.
C'est pas exactement un mélange… Tout est défini autour de la même fonctionnalité: Un état x représentant la fin d'exécution (erreur ou réussite) de y, déclenche un événement z. C'est simple: (Résultat + )Signal.
Si je veux fournir une API asynchrone dans laquelle je ne veux pas exposer de "Wait()" (parce que je considère que ça serait un risque de bloquer un thread pour tel ou tel évènement), je ne vais pas pouvoir utiliser Task.
Sauf que si ton API asynchrone ne doit pas bloquer sur un Wait(), sinon c'est un bug. Si tu implémentes une API sans interface (ce qui est presque toujours le cas ?), tu ne dois pas être lié à un contexte de synchronisation. Autrement dit, ton code doit s'exécuter, et s'exécutera sur le ThreadPool par défaut, donc Wait() ne posera pas de problème. (cf. ici)
En revanche, si tu as une application console dont le seul but est d'exécuter une commande qui est implémentée de manière asynchrone, ben le Wait() sera ton meilleur ami. (Exemple pas pris au hasard, c'est juste… Super fréquent)
Je suis assez d'accord avec ce que raconte ce mec sur la séparation claire des APIs synchrones et asynchrones, donc un petit lien plutôt que de tout recopier ici :
http://blog.ometer.com/2011/07/24/callbacks-synchronous-and-asynchronous/
Ben ouais mais du coup tu mélanges tout là, ça n'a absolument aucun rapport avec le schmilblick :/
Les Task ne sont pas des Callbacks (l'intérêt étant justement d'inverser ce paradigme), et en dehors du Wait() (sans rapport avec de quelconques callbacks), il n'y a absolument rien de synchrone sur les Tasks. Si on faisait le parallèle avec ce que le mec raconte, les task tombent à 100% dans le cas asynchrone, ce qui est normal, puisque c'est leur but… (i.e. La continuation est toujours exécuté après la fin d'exécution de la tâche.)
Après, en tant que développeur tu es libre de faire ta propre bidouille (e.g. avec TaskCompletionSource<T>, ou avec ManualResetEventSlim…) et de te tirer une balle dans le pieds, mais c'est quand même pas si facile que ça.
avatar
Le scénario de notre univers a été rédigée par un bataillon de singes savants. Tout s'explique enfin.
T'as un problème ? Tu veux un bonbon ?
[CrystalMPQ] C# MPQ Library/Tools - [CrystalBoy] C# GB Emulator - [Monoxide] C# OSX library - M68k Opcodes

283

GoldenCrystal (./282) :
une API sans interface


C'est une AP?

284

+utilisateur cheeky
(oubli tongue)
avatar
Le scénario de notre univers a été rédigée par un bataillon de singes savants. Tout s'explique enfin.
T'as un problème ? Tu veux un bonbon ?
[CrystalMPQ] C# MPQ Library/Tools - [CrystalBoy] C# GB Emulator - [Monoxide] C# OSX library - M68k Opcodes

285

./282 : tu parles à la fois de fournir une API et d'attendre sur un "Wait()" donc je pense qu'on ne se comprend pas. Il est question ici de *fournir* une API, et donc soit de demander une callback, soit d'exposer un évènement, soit de retourner une Task (qui joue ici le rôle qu'on appelle "future" ou "deferred" dans d'autres langages, sachant que Task est un truc hybride qui fait à la fois future et promesse entre d'autres trucs). Ce ne sont que plusieurs implémentations possibles pour la même chose, il n'y a strictement aucune différence au niveau de l'exécution. En revanche, proposer un seul objet est confus : si on me retourne une task pour faire ce que j'aurais voulu faire avec d'autres frameworks en retournant une future, je donne à mon client un objet sur lequel il peut par exemple appeler "Start()", ce qui est probablement une erreur vu que l'API a déjà démarré cette task, à moins que non, aucun moyen de savoir (enfin si, avec les 300 propriétés à ma disposition il y en a surement une qui permet de savoir ça, mais c'est vraiment la dernière chose que j'ai envie de faire).
avatar
All right. Keep doing whatever it is you think you're doing.
------------------------------------------
Besoin d'aide sur le site ? Essayez par ici :)

286

(Heu déjà, c'est toi qui cause d'asynchrone et de Wait() en premier lieu, je ne fais que te répondre hein… Il était question de fournir une API via Task, donc tout ce qui est callback ou autre ça dégage… Et justement si, y'a de grosses différences dans la gestion des Threads, c'est là où la TPL de .NET tire son épingle du jeu. tongue)

Le principe général c'est qu'on te fourniras « jamais » de tâche non démarrée… (ou oui, on peut toujours faire de la merde, rien ne l'interdit tongue) C'est simple, on te retourne une tâche, et tu l'attends quand ça te chante. (ou bien tu ne l'attends pas, mais c'est pas recommandé et probablement contreproductif)
La méthode Start sert si tu as besoin de bidouiller des choses avec l'objet Task avant qu'il soit démarré. (i.e. tu as besoin de séparer la construction et l'exécution, par exemple pour mettre en cache l'instance de l'objet Task), ce qui n'est pas le cas général.

La finalité est assez simple:
Tu as un point de vue « fournisseur » où tu fournis une tâche « démarrée » d'une de ces trois façons:
- Contrôlée extérieurement (TaskCompletionSource)
- Représentant l'exécution d'une méthode plus ou moins coûteuse en CPU (à priori sur un autre thread)
 - Représentant la continuation d'une autre tâche (via .ContinueWith)
Tu as un point de vue « consommateur » où on te fournis une tâche qui se finira un jour: (Ou qui est déjà finie, peu importe, le comportement est identique)
 - Tu peux te chaîner dessus avec .ContinueWith pour exécuter du code à la fin de la méthode.
- Tu t'en fous de l'asynchrone, mais tu as besoin de synchroniser un thread, donc tu utilises le WaitHandle pour attendre le signal de fin.
- Tu n'as pas de boucle d'évènement, donc tu utilises Wait(), pour attendre la fin.
Et le reste, et c'est très important, tu t'en fous.

Bref, si tu fournis ton API via Task, c'est une API qui suit le modèle asychrone. i.e. t'es pas obligé de bloquer (volontairement) ton thread pour attendre la fin.

(Oh et on a pas parlé du support des jetons d'annulation, mais je suppose que tu trouves ça superflu également ? tongue)
avatar
Le scénario de notre univers a été rédigée par un bataillon de singes savants. Tout s'explique enfin.
T'as un problème ? Tu veux un bonbon ?
[CrystalMPQ] C# MPQ Library/Tools - [CrystalBoy] C# GB Emulator - [Monoxide] C# OSX library - M68k Opcodes

287

Tu continues (depuis plusieurs posts même) à m'expliquer comment utiliser l'objet "Task". C'est intéressant, mais MSDN en dit tout autant et je pense que tu passes à côté de ce que j'essaie d'expliquer ; ce que je te propose de faire c'est de regarder comment c'est implémenté ailleurs qu'en .NET et de constater (ou non, dans ce cas la discussion pourra s'arrêter) une chose : bien que les concepts soient les mêmes (i.e. .NET ne permet rien de plus ou de moins), ils sont nettement séparés dans à peu près tous les frameworks là où .NET fournit un unique objet magique "Task" qui fait tout à la fois. Je sens bien que j'ai un peu de mal à te faire comprendre ça, peut-être parce que ça te semble un peu trop naturel à force de l'avoir utilisé, mais tu l'illustres toi-même avec tes exemples : tu me sépares correctement une "vue fournisseur" et une "vue consommateur", sauf que tes deux parties voient tous les deux le même objet "Task" (mais ne vont pas l'utiliser de la même façon ; chacun a son petit sous-ensemble de méthode, mais au lieu d'avoir deux objets séparés on en a un seul qui fait tout).

Je ne trouve rien superflu (où ais-je dit ça ?), je trouve simplement .NET très confus à ce niveau, et je jette la faute sur cette sacro-sainte rétrocompatibilité qu'il aurait vraiment fallu jeter, les bases étant bien pourries. Pour les jetons d'annulation, même constat : c'est un concept absolument indispensable sans lequel le framework serait incomplet (oh tiens, bonjour IAsyncResult), mais c'est également un concept qui peut être totalement dissocié des tâches elles-mêmes, alors que là on se retrouve avec un truc qui embarque à la fois l'annulation et un mécanisme de gestion d'erreur. Quel intérêt ?
avatar
All right. Keep doing whatever it is you think you're doing.
------------------------------------------
Besoin d'aide sur le site ? Essayez par ici :)

288

Non en fait je vois bien que tu considères que ça fait plusieurs choses différentes… Mais c'est juste pas mon avis. (Et je pense pas être la seule personne dans ce cas, m'enfin)
Pour moi ça fait bien une seule et même chose comme tout bon objet à part entière… Il fournit différente possibilités à l'utilisateur (.ContinueWith, .Wait, etc.) mais ça fournit bien exactement le même service au final.
Si j'ai séparé les « méthodes » en deux catégories, c'est simple : En POO, quel que soit l'objet, quelqu'un construit l'objet, et quelqu'un l'utilise… Comme n'importe quel objet. La plupart des objets font cela via des méthodes "Factory" ou via des constructeurs, c'est exactement le cas de Task, pourtant cela semble te gêner.
J'admet que le cas de Start() ou RunInline() ne soient pas du meilleur effet à ce niveau, ça fait deux méthodes un peu ambiguës en tout et pour tout. (Je t'avouerais même que j'ai mis du temps à comprendre pourquoi elles étaient là tant je m'en sers peu)

Pour le qui doit être séparé l'a déjà été: Un observateur normal ne peut jamais déterminer ce qui contrôle le Task. (Un delegate ou un TaskCompletionSource)
Au même titre qu'un CancellationToken (qui n'a aucun lien direct avec les Task, je tiens à noter) est controllé par un CancellationTokenSource quelque part ailleurs… (Les tâches utilisent (optionnellement) CancellationToken, mais pas l'inverse, attention…)

Quand à la mécanique de gestion d'erreur, c'est peut-être parce que si tu ne les gères pas, ton programme plante ? (Non, c'est plus vrai maintenant, car ça faisait crasher trop d'applications)
Je rappelle qu'à la base on parlait de code asynchrone en multithread, et je disais que justement, .NET est très bien fichu à ce niveau là. Prenons cet exemple (bidon) en C#:async Task<string> GetProcessedData(Uri uri) { var webClient = new WebClient(); string data; try { data = await webClient.DownloadStringTaskAsync(uri).ConfigureAwait(false); } catch (Exception ex) { Logger.Error("An exception occured during download.", ex); throw; } return ProcessData(data);. }C'est quand même difficile de faire mieux que async/await niveau lisibilité. (Et on dit merci le compilateur et merci Task<T>)
Maintenant, peux-tu m'expliquer comment tu gères les exceptions si Task (ou n'importe quel awaitable) ne te remonte pas d'erreur d'exécution ?


(NB: Tu noteras que là par exemple, c'est exactement la même chose que Task<T> et TaskCompletionSource<T>, juste avec des noms et une syntaxe différente, est-ce que ça te gêne autant ?)
avatar
Le scénario de notre univers a été rédigée par un bataillon de singes savants. Tout s'explique enfin.
T'as un problème ? Tu veux un bonbon ?
[CrystalMPQ] C# MPQ Library/Tools - [CrystalBoy] C# GB Emulator - [Monoxide] C# OSX library - M68k Opcodes

289

avatar
Zeroblog

« Tout homme porte sur l'épaule gauche un singe et, sur l'épaule droite, un perroquet. » — Jean Cocteau
« Moi je cherche plus de logique non plus. C'est surement pour cela que j'apprécie les Ataris, ils sont aussi logiques que moi ! » — GT Turbo

290

./289: C'est beau
avatar
Proud to be CAKE©®™


GCC4TI importe qui a problème en Autriche, pour l'UE plus et une encore de correspours nucléaire, ce n'est pas ytre d'instérier. L'état très même contraire, toujours reconstruire un pouvoir une choyer d'aucrée de compris le plus mite de genre, ce n'est pas moins)
Stalin est l'élection de la langie.

291

surréaliste xD
x = inportb(N) * 256 + inportb(N+1);

(where inportb() returns unsigned char) and found that it generated a mov instruction instead of a shift or multiply for the times-256...

Là, j'avoue que ça me pose question. Quel est le type de x ?
Si x est un char, le mec est un peu con, donc je pense pas que ce soit ça.
Sinon, je suis même pas foutu de savoir ce qui se passe, mettons si x est un int, avec sizeof(int)>sizeof(char) :
Est-ce que chaque membre de l'expression est promu en int, puis les opérations sont effectuées ?
Est-ce que la promotion de l'ensemble de l'expression dans le type de x n'est faite qu'une fois l'évaluation de la rvalue terminée ?
...

Je me rends compte que je sais même pas comment s'y prend C #shameonme#

292

Honnêtement, je n'en suis plus sûr et je n'ai pas le K&R sous la main.

Je préfère toujours caster explicitement et utiliser des parenthèses (voire décomposer l'opération). Je reconnais que c'est feignasse, mais je préfère écrire du code un peu lourd mais sans ambiguïté, plutôt que du code plus court et risquer de me vautrer sur un piège que j'aurai oublié. Et des pièges, c'est pas ce qui manque en C.
avatar
Zeroblog

« Tout homme porte sur l'épaule gauche un singe et, sur l'épaule droite, un perroquet. » — Jean Cocteau
« Moi je cherche plus de logique non plus. C'est surement pour cela que j'apprécie les Ataris, ils sont aussi logiques que moi ! » — GT Turbo

293

Pas sur que ca soit dans la norme, en tout cas tout ce qui touche a l'optimisation.

Si X est d'un type d'au moins 16bit, c'est l'optimiseur qui se foire, la raison est dure a dire
avatar
Proud to be CAKE©®™


GCC4TI importe qui a problème en Autriche, pour l'UE plus et une encore de correspours nucléaire, ce n'est pas ytre d'instérier. L'état très même contraire, toujours reconstruire un pouvoir une choyer d'aucrée de compris le plus mite de genre, ce n'est pas moins)
Stalin est l'élection de la langie.

294

(au passage, avec ce code, on ne sait pas quel port I/O sera lu en premier. Il y a du matos pour lequel c'est important, donc il faut de toute façon décomposer l'opération dans ce cas.)

Godzil > l'évaluation des expressions avec des types différents est bien spécifiée dans le K&R, ça n'est pas censé dépendre du compilo.
avatar
Zeroblog

« Tout homme porte sur l'épaule gauche un singe et, sur l'épaule droite, un perroquet. » — Jean Cocteau
« Moi je cherche plus de logique non plus. C'est surement pour cela que j'apprécie les Ataris, ils sont aussi logiques que moi ! » — GT Turbo

295

l'eval oui, l'optimisation non que je sache..

Et la on a affaire a une optimisation foireuse..

(et ca ne sera pas la premiere, ni derniere qu'un optimisateur fait n'importe quoi...)
avatar
Proud to be CAKE©®™


GCC4TI importe qui a problème en Autriche, pour l'UE plus et une encore de correspours nucléaire, ce n'est pas ytre d'instérier. L'état très même contraire, toujours reconstruire un pouvoir une choyer d'aucrée de compris le plus mite de genre, ce n'est pas moins)
Stalin est l'élection de la langie.

296

./288 : je ne vois pas en quoi ton lien Wikipedia soutien ton avis, au contraire, les futures et les promises sont justement un moyen de séparer la vue fournisseur et la consommateur, alors que "task" joue le rôle des deux à la fois. Je me répète (encore...) : ce que propose .NET est tout à fait fonctionnel, par exemple c'est très bien d'avoir une gestion des exceptions, mais il n'y a aucune séparation des concepts. Désolé, je vois que tu ne comprends pas du tout ce que j'essaie d'expliquer depuis plusieurs posts mais je ne vois pas d'autre façon de présenter les choses. Si tu es content avec ce que propose .NET, tant mieux, je n'essaie pas de dire que ça ne répond à aucun besoin comme ce que tu as l'air de penser.

Si ça peut aider, pour répondre à ton NB, oui c'est exactement la même chose sous deux syntaxes différentes. Je ne vois en revanche pas le rapport avec ce que j'explique depuis le début, à aucun moment il n'a été question de syntaxe ou de lisibilité.
avatar
All right. Keep doing whatever it is you think you're doing.
------------------------------------------
Besoin d'aide sur le site ? Essayez par ici :)

297

#include <stdio.h> #include <stdlib.h> int main() { unsigned char a = 0x12, b = 0x34; unsigned int c = a * 256 + b; printf("%x\n", c); return 0; }affiche bien "1234" avec GCC. Pareil si on remplace int par short. Je vois pas où est le bug ici ?
avatar
Zeroblog

« Tout homme porte sur l'épaule gauche un singe et, sur l'épaule droite, un perroquet. » — Jean Cocteau
« Moi je cherche plus de logique non plus. C'est surement pour cela que j'apprécie les Ataris, ils sont aussi logiques que moi ! » — GT Turbo

298

Aztec C? (et puis une ligne sans tout le contexte du code..

Si bien il fait un truc a la con genre
x = readio(N) * 256 + readio(N+1); y = touchblabla(x & 0xFF);

Comme je crois qu'un retour "volatile" n'a pas de sens, l'optimiseur peux discarder l'appel a readio(N) car la valeur n'est pas utilise...


Hum GCC optimise (trop)...
#include <stdio.h> #include <stdlib.h> #include <stdint.h> uint8_t readIo(uint8_t port) { return 0x42; } uint8_t TouchMyBlabla(uint8_t blabla) { return blabla * 2; } int main() { uint32_t N = 126; uint16_t x = readIo(N) * 256 + readIo(N-1); printf("%d\n", TouchMyBlabla(x & 0xFF)); return 0; }
00000000004005a7 <main>: 4005a7: 48 83 ec 08 sub $0x8,%rsp 4005ab: be 84 00 00 00 mov $0x84,%esi 4005b0: bf b4 06 40 00 mov $0x4006b4,%edi 4005b5: 31 c0 xor %eax,%eax 4005b7: e8 fc fe ff ff callq 4004b8 <printf@plt> 4005bc: 5a pop %rdx 4005bd: 31 c0 xor %eax,%eax 4005bf: c3 retq
gol

en -O0 il appelle readIo et l'autre, la il met une constante sad

Humpf meme avec ca
uint8_t readIo(uint8_t port) { if (v> 128) return 0x42; else return port^ 0xAA; }
il optimise avec une constante...

Par contre
uint8_t readIo(uint8_t port) { return rand(); } uint8_t TouchMyBlabla(uint8_t blabla) { return blabla * 2; } int main() { uint32_t N = 126; uint16_t x = readIo(N) * 256 + readIo(N-1); printf("%d\n", TouchMyBlabla(x & 0xFF)); return 0; }

en -O30000000000400610 <main>: 400610: 48 83 ec 08 sub $0x8,%rsp 400614: e8 ef fe ff ff callq 400508 <rand@plt> 400619: e8 ea fe ff ff callq 400508 <rand@plt> 40061e: 8d 34 00 lea (%rax,%rax,1),%esi 400621: bf 34 07 40 00 mov $0x400734,%edi 400626: 31 c0 xor %eax,%eax 400628: 81 e6 fe 00 00 00 and $0xfe,%esi 40062e: e8 b5 fe ff ff callq 4004e8 <printf@plt> 400633: 31 c0 xor %eax,%eax 400635: 48 83 c4 08 add $0x8,%rsp 400639: c3 retq

Il appel 2x rand il ne sais pas voir que seul la partie basse de X est utilise..
avatar
Proud to be CAKE©®™


GCC4TI importe qui a problème en Autriche, pour l'UE plus et une encore de correspours nucléaire, ce n'est pas ytre d'instérier. L'état très même contraire, toujours reconstruire un pouvoir une choyer d'aucrée de compris le plus mite de genre, ce n'est pas moins)
Stalin est l'élection de la langie.

299

Godzil (./298) :
Il appel 2x rand il ne sais pas voir que seul la partie basse de X est utilise..


Non, il sait que rand utilise des variables globales pour mémoriser son état, et que ne pas l'appeler changerait l'état de ton programme (tu aurais des nombres aléatoires différents) et c'est donc une optimisation interdite.

300

moui
avatar
Proud to be CAKE©®™


GCC4TI importe qui a problème en Autriche, pour l'UE plus et une encore de correspours nucléaire, ce n'est pas ytre d'instérier. L'état très même contraire, toujours reconstruire un pouvoir une choyer d'aucrée de compris le plus mite de genre, ce n'est pas moins)
Stalin est l'élection de la langie.