Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

boucle dans un tableau indicé de façon non consécutive

6 views
Skip to first unread message

jero

unread,
Sep 4, 2006, 7:03:58 AM9/4/06
to
Bonjour

je suis en train de me prendre les pieds dans le tapis ...

j'ai récupéré des données dans une base de données via
XMLHttpRequest jusque là tout va bien.
j'ai stocké ces données dans une variable globale de mon javascript :

var window.mesDonnees = new Array();

Afin de stocké chaque colonne de chaque ligne récupérée dans ma
base j'ai imbriqué un tableau dans mon tableau windows.mesDonnes que
j'ai indicé avec l'identifiant numérique de chaque élément
récupéré :

var window.mesDonnees[identifiantNumérique] = new Array();

de sorte de pouvoir y stocker les valeur récupérées dans chaque
colonne

var window.mesDonnees[identifiantNumérique][0] = valeurColonne_0
var window.mesDonnees[identifiantNumérique][1] = valeurColonne_1
etc...

je ne trouve pas de methode pour faire une boucle dans mon tableau au
niveau ou il est indicé par les identifiants numériques, dans la
mesure où ils ne sont pas nécessairement consécutifs !

de sorte que le classique

for ( var i = 0 ; i < window.mesDonnees.length ; i++) {
window.mesDonnees[i] faitQuelqueChose;
}

n'est pas opérationnel ...

connaissez vous une méthode qui pourrai fonctionner ? un genre
d'équivalent à la boucle 'for each' du PHP ?

D'avance grand merci !
Jérôme

Laurent vilday

unread,
Sep 4, 2006, 7:57:00 AM9/4/06
to
jero a écrit :

> je suis en train de me prendre les pieds dans le tapis ...

visiblement oui :)

> j'ai stocké ces données dans une variable globale de mon javascript :
> var window.mesDonnees = new Array();

pas de /var/ ici puisque tu ajoute une propriété à un objet (window)
existant.

juste
window.mesDonnees = new Array();

new Array() est transformable à volonté par []

donc
window.mesDonnees = [];

> Afin de stocké chaque colonne de chaque ligne récupérée dans ma
> base j'ai imbriqué un tableau dans mon tableau windows.mesDonnes que
> j'ai indicé avec l'identifiant numérique de chaque élément
> récupéré :
>
> var window.mesDonnees[identifiantNumérique] = new Array();

> var window.mesDonnees[identifiantNumérique][0] = valeurColonne_0
> var window.mesDonnees[identifiantNumérique][1] = valeurColonne_1
> etc...
>
> je ne trouve pas de methode pour faire une boucle dans mon tableau au
> niveau ou il est indicé par les identifiants numériques, dans la
> mesure où ils ne sont pas nécessairement consécutifs !

// puisque mesDonnees est un hash,
// tu veux en fait un objet et un pas un array
window.mesDonnees = {};

puis

for ( var index in window.mesDonnees )
{
var tableau = window.mesDonnees[index];
}

--
laurent

ASM

unread,
Sep 4, 2006, 8:07:14 AM9/4/06
to
jero a écrit :
> Bonjour

Bonjour,

> je suis en train de me prendre les pieds dans le tapis ...
>
> j'ai récupéré des données dans une base de données via
> XMLHttpRequest jusque là tout va bien.

on ne dirait pas :-)

> j'ai stocké ces données dans une variable globale de mon javascript :
>
> var window.mesDonnees = new Array();
>
> Afin de stocké chaque colonne de chaque ligne récupérée dans ma
> base j'ai imbriqué un tableau dans mon tableau windows.mesDonnes que
> j'ai indicé avec l'identifiant numérique de chaque élément
> récupéré :
>
> var window.mesDonnees[identifiantNumérique] = new Array();

Si vraiment tu veux faire ça via JS, à mon idée et au plus simple, ton
php devra créer un tableau javascript des lignes, chaque ligne étant un
tableau des colonnes de la ligne.
Mais via php il est aussi facile de faire l'inverse
tableau des colonnes des tableaux des lignes

echo "var mesDonnees = new Array();"
$i = 0;
machin-truc php d'esstraction des lignes de la bdd habituel
echo "mesDonnees[$i] = new Array();"
machin-truc php pour séparer les colonnes
for($j=0; $j<$machintrucphp.count;$j++)
echo "mesdonnes[$i][$j] = $trucbiduleColonnePhp;"

Après, en JS, il suffit de faire écrire le table,

var L = mesdonnees.length;
vac C = mesdonnees[0].length;
var t = '<table>\n';
for(var i=0;i<L;i++)
{
t += '<tr>\n';
for(var j=0;j<c;j++)
t += '<td>'+mesdonnes[i].[j]+'<\/td>';
t += '<\/tr>\n';
}
t += '<\/table>';

document.getElementById('truc').innerHTML = t;


trier un tableau JavaScript à 2 entrees :
http://www.asp-php.net/scripts/scripting/array_sort.php

Perso, puisqu'on a la chance d'avoir du php
je pense que ce tri aurait plus sa place en php
lors de sa requete à la bdd
(qui printera directement le bazar html inclus par XMLHttpRequest)

C'est le grand PLUS du XMLHttpRequest de faire lien avec du vrai php.

Gosso modo, la méthode est identique à appeller une page php dans une
iframe (sauf qu'on n'a besoin que du code du table au lieu d'une page
complète).

--
Stephane Moriaux et son [moins] vieux Mac

jero

unread,
Sep 4, 2006, 8:17:27 AM9/4/06
to
Merci je vais essayer cette piste là !
jérôme.


Laurent vilday a écrit :

YD

unread,
Sep 4, 2006, 1:15:18 PM9/4/06
to
Laurent vilday a écrit :

> jero a écrit :
>> je suis en train de me prendre les pieds dans le tapis ...
>
> visiblement oui :)

Non, il ne manque qu'un petit coup de pouce dans la bonne direction.

>
>> j'ai stocké ces données dans une variable globale de mon javascript :
>> var window.mesDonnees = new Array();
>
> pas de /var/ ici puisque tu ajoute une propriété à un objet (window)
> existant.

Ben c'est une faute de frappe, sinon le script n'aurait pas été bien
loin...

> juste
> window.mesDonnees = new Array();
>
> new Array() est transformable à volonté par []
>
> donc
> window.mesDonnees = [];

Ça ajoute quoi d'écrire [] au lieu de Array() ou new Array() ???
Idem pour {} au lieu de Object()

>
>> Afin de stocké chaque colonne de chaque ligne récupérée dans ma
>> base j'ai imbriqué un tableau dans mon tableau windows.mesDonnes que
>> j'ai indicé avec l'identifiant numérique de chaque élément
>> récupéré :
>>
>> var window.mesDonnees[identifiantNumérique] = new Array();
>> var window.mesDonnees[identifiantNumérique][0] = valeurColonne_0
>> var window.mesDonnees[identifiantNumérique][1] = valeurColonne_1
>> etc...
>>
>> je ne trouve pas de methode pour faire une boucle dans mon tableau au
>> niveau ou il est indicé par les identifiants numériques, dans la
>> mesure où ils ne sont pas nécessairement consécutifs !
>
> // puisque mesDonnees est un hash,
> // tu veux en fait un objet et un pas un array
> window.mesDonnees = {};

En passant un Array (majuscule STP) est un Object qui dispose de toutes
les propriétés des objets Javascript et d'autres spécifiques en plus.

> for ( var index in window.mesDonnees )

Cela suffit et fonctionne pour un Array. Donc :

mesDonnees = new Array();
mesDonnees[identifiantNumerique] = new Array();
mesDonnees[identifiantNumerique][0] = valeurColonne_0;
mesDonnees[identifiantNumerique][1] = valeurColonne_1;

//etc.

for (identifiantNumerique in mesDonnees)
{
//on ne récupère que les indices définis !
mesDonnees[identifiantNumerique]
}

Quant au var mesDonnees ou window.mesDonnees, tout dépend de la
portée souhaitée pour cette variable et de l'endroit où on la
définit.

--
Y.D.

Laurent vilday

unread,
Sep 4, 2006, 3:20:12 PM9/4/06
to
YD a écrit :

> Laurent vilday a écrit :
>> jero a écrit :
>>> j'ai stocké ces données dans une variable globale de mon javascript :
>>> var window.mesDonnees = new Array();
>>
>> pas de /var/ ici puisque tu ajoute une propriété à un objet (window)
>> existant.
>
> Ben c'est une faute de frappe, sinon le script n'aurait pas été bien
> loin...

Et ? Faute de frappe ou pas, c'est pas correct d'utiliser /var/ lors de
la déclaration d'une propriété, qu'on soit sur l'objet window ou
n'importe quel autre. Donc il aurait fallu utiliser une boule de cristal
pour deviner ce qui était une faute de frappe ou pas ? Et laisser
l'erreur en l'état dans les archives des news ? Désolé mais non. Et
plutot que de modifier la syntaxe initiale j'ai préféré rester sur une
base commune à ce qu'avait écrit l'OP, car sans le code source *complet*
on a aucun moyen de savoir ce qu'il veut faire et comment il veut le faire.

On peut très bien considérer que l'OP a sa fonction définie de telle manière

function remplir()
{
window.mesDonnees = 'foo';
}

Et là, c'est pas lui rendre service que de lui dire qu'il suffirait de
faire ceci pour arriver au même résultat, ça conduit à de TRES mauvaises
façons de coder !

function remplir()
{
mesDonnees = 'foo';
}

Tout simplement parce qu'on a *aucun* moyen de connaître la façon dont
est appelée sa méthode de remplissage et ce qu'il veut en faire. Et lui
donner un *mauvais* exemple n'est pas rendre service ni à lui ni aux
lecteurs de fclj.

> Ça ajoute quoi d'écrire [] au lieu de Array() ou new Array() ???
> Idem pour {} au lieu de Object()

Preque aucune différence, si ce n'est que c'est moins de caractères,
c'est "transmissible" par JSON et que new Array() ainsi que new Object()
sont des notations d'un age antidéluvien (cad IE4/NS4 c'est dire si
c'est obsolète). Les navigateurs dit "modernes" (ceux qui se faisaient
appeler 4eme génération il y a quelques temps) permettent l'utilisation
de la notation courte, pourquoi s'en priver ?

D'autant plus que la notation courte permet d'écrire ceci :

var foo = [5];

alors qu'avec la notation longue

var bar = new Array(5);

n'aura *pas* du tout la même signification.

alert(foo.length) ==> 1
alert(bar.length) ==> 5

Mieux encore, la notation courte permet également des définitions que
new Array() ne permettra jamais aussi simplement

var foo = [[1,2,3],[4,5,6],[7,8,9]];
http://www.json.org/

>> // puisque mesDonnees est un hash,
>> // tu veux en fait un objet et un pas un array
>> window.mesDonnees = {};
>
> En passant un Array (majuscule STP) est un Object qui dispose de toutes
> les propriétés des objets Javascript et d'autres spécifiques en plus.

Hurm, majuscule, euh, seulement si j'écris du code qui doit être
interprété, pas que j'en parle. Merci de me laisser écrire un
commentaire comme je l'entend !

> Cela suffit et fonctionne pour un Array. Donc :

Non ! Ce n'est pas parce que, oh miracle, ça à l'air de passer que c'est
la bonne solution. Pourquoi pas utiliser un new Boolean(), new String(),
new Regexp() ou encore pendant qu'on est à faire n'importe quoi, un new
Function() ?
http://developer.mozilla.org/en/docs/Core_JavaScript_1.5_Reference:Global_Objects:Array
<quote>
An array is an ordered set of values associated with a single variable
name. *Note that you shouldn't use it as an associative array, use
Object instead.*
</quote>
http://www.andrewdupont.net/2006/05/18/javascript-associative-arrays-considered-harmful/

Le type Array dans le cas de l'OP n'est donc tout simplement pas la
solution à retenir.

var tbl = [];
tbl['cleOne'] = 'foo';
tbl['cleTwo'] = 'bar';
tbl[5] = 'foobar';
// tbl.cleOne et tbl.cleTwo serait une meilleure notation,
// mais c'est pour la compréhension de l'exemple
// que je garde exprès les crochets autour

alert(tbl.length);
// == 6 ?!?!

Les tableaux avec indexes *numériques séquentiels* (Array) ne sont donc
*pas* (jamais) à utiliser lorsque les clés ne sont pas numériques
séquentielles (cad lorsque l'on a clé/valeur au lieu de index/valeur).
On est donc bien dans le cas d'un tableau associatif (hash, clé/valeur)
et le plus proche en javascript (bien que ça n'existe pas) c'est le type
Object et non pas Array !

> Quant au var mesDonnees ou window.mesDonnees, tout dépend de la
> portée souhaitée pour cette variable et de l'endroit où on la
> définit.

Oui, on est d'accord, mais c'est pas une raison pour indiquer de
mauvaises pistes et considérer que le lecteur pourra faire la différence
entre ce qui doit être fait, ce qui ne doit pas l'être et ce qui est
sous entendu !

Javascript est déjà suffisemment mal compris pour ne pas indiquer de
mauvaises "solutions" comme tu viens de le faire dans ton message.

--
laurent

jero

unread,
Sep 4, 2006, 7:33:18 PM9/4/06
to
trés trés technique votre échange et je ne compte pas vraiment
m'imicer dedans à peine foutu que je suis de ne pas me vautrer à
force de tapis prets à se saisir de mes pieds gauches....

cependant je retiens une chose c'est que le code source complet aide à
la compréhension de ce que je voulais faire ; soit :

j'ai une xmlHttpRequest à l'issue de laquelle je traite des données
de la façon suivante :


donneesTab =
_XmlHttpRequest.responseXML.getElementsByTagName('mesDonnees);
window._cacheDonnees = new Array();

for (i=0; i < donneesTab.length; ++i) {
var idDonnees = donnesTab[i].childNodes[0].firstChild.data;
window._cacheDonnees[idDonnees][0] =
donneesTab[i].childNodes[1].firstChild.data;
}


plus loin dans une fonction j'écris ceci

var liste = window._cacheDonnes;
for ( var indice in liste ) {
var mesDonnees = liste[indice];
div = document.createElement('div');
// il existe une div qui s'appelle divParent
divParent.appendChild(div);
div.id = indice;
div.title = mesDonnees[0]
// etc ....
}

ce qui fait exactement ce que je recherchais, et grâce à votre aide
généreuse !
merci encore.
jérôme

PS. j'ai retranscrit mon code source : il se peut qu'une/des fautes de
frappe s'y soit glissée/s

YD

unread,
Sep 5, 2006, 2:26:42 AM9/5/06
to
Je ne vais pas répondre dans le fil, ça serait indigeste, mais reprendre
quelques points et développer.

1) L'OP devait-il utiliser un Array ?

Dans la mesure où il dit utiliser des identifiants numériques (qu'on peut
supposer entiers et inférieurs à la valeur maximale possible), pourquoi
pas ? Par ailleurs on ne sait pas quelles propriétés spécifiques aux Arrays
sont utilisées. S'il n'y en a aucune, il est alors possible d'utiliser
des Objects mais pourquoi pas un Array qui permettra de connaître très
vite le plus grand identifiant numérique utilisé (mesDonnees.length-1).


2) La question de l'OP était : existe-t-il un moyen de parcourir un Array
qui n'est pas 'dense' (qui ne possède pas une valeur pour chaque indice
inférieur à sa propriété length) ?

La réponse est oui, for(p in o) qui énumérera en p les propriétés
énumérables définies de l'objet o. Ceci n'est pas propre aux Arrays mais
à tous les objets JS. Ça présente l'avantage pour les Arrays de ne donner
que les "indices" pour lesquels une valeur est définie. Il donnera également
les autres propriétés qu'on aura pu ajouter à l'objet Array... Se servir
dans les Arrays des méthodes et opérateurs définis pour les Objects c'est
prévu. Et ce n'est pas un miracle, c'est de la programmation orientée
objet -- enfin, tu dois le savoir.


3) Sur l'utilisation de l'objet global du navigateur : window.
Tu prétends que


function remplir() {window.mesDonnees = 'foo';}

est 'mieux' que


function remplir() {mesDonnees = 'foo';}

Je ne te suis pas là-dessus. Si une variable est affectée d'une valeur
dans une fonction et qu'elle n'a pas été déclarée auparavant *dans la
fonction* c'est qu'elle est appartient à un contexte d'exécution 'supérieur'
voire, /in fine/, au niveau global. La bonne utilisation de la portée
des variables vient avec la longueur et la complexité des scripts.

L'intérêt d'une écriture comme window.mesDonnees est à mon sens davantage
de permettre de tester l'existence d'une variable mesDonnees et non de la
définir...


4) Ce que tu appelles "notation courte" versus "notations d'un âge
antidéluvien" (quel argument !)

Pour ces notations abrégées de l'initialisation d'un Array ou Object,
la norme ECMA262 emploie l'expression Array Initialiser :
"An array initialiser is an expression describing the initialisation
of an Array object, written in a form of a literal."
Dans ce cas la première étape que doit faire le moteur JS, face à ce
type d'écriture :
"1. Create a new array as if by the expression new Array()."
Dans un cas on fait appel explicitement au constructeur, dans l'autre
c'est implicite.
Tu peux donc trouver cela très pratique mais ce n'est qu'une facilité
d'écriture et n'est pas particulièrement à recommander. On se sert de
l'un ou l'autre selon ses besoins et préférences -- et ce n'est pas
parce qu'un script est abscons qu'il est forcément 'mieux'.


Laurent vilday a écrit :


> Javascript est déjà suffisemment mal compris pour ne pas indiquer de
> mauvaises "solutions" comme tu viens de le faire dans ton message.

Ça s'appelle une attaque ad hominem ? Ou alors tu es *vraiment* persuadé
de détenir la vérité sur le bon usage du Javascript ?


--
Y.D.

Laurent vilday

unread,
Sep 5, 2006, 5:47:38 AM9/5/06
to
YD a écrit :

> Je ne vais pas répondre dans le fil, ça serait indigeste, mais reprendre
> quelques points et développer.

Mouais évidemment, ça va aider à comprendre c'est certain. D'un autre
côté, ça va te permettre de me préter des paroles qui ne sont pas les
miennes, belle technique.

> 1) L'OP devait-il utiliser un Array ?

Non !

> Dans la mesure où il dit utiliser des identifiants numériques (qu'on peut
> supposer entiers et inférieurs à la valeur maximale possible), pourquoi
> pas ?

Tout simplement parce qu'il dit *aussi* ceci :

<cite>


je ne trouve pas de methode pour faire une boucle dans mon tableau au
niveau ou il est indicé par les identifiants numériques, dans la mesure
où ils ne sont pas nécessairement consécutifs

</cite>

Toute la problématique est résumé avec ces 3 mots :

"pas nécessairement consécutifs"

> Par ailleurs on ne sait pas quelles propriétés spécifiques aux Arrays
> sont utilisées. S'il n'y en a aucune, il est alors possible d'utiliser
> des Objects mais pourquoi pas un Array qui permettra de connaître très
> vite le plus grand identifiant numérique utilisé (mesDonnees.length-1).

Non, ce n'est pas consécutifs, d'après ce qu'il dit il a potentiellement
ceci :

mesDonnees[0] = [];
mesDonnees[1] = [];
mesDonnees[31] = [];
mesDonnees[20] = [];
mesDonnees[8] = [];

alert(mesDonnees.length - 1);
// 31

31 ?!?! Ce n'est pas vrai, tout simplement.

Je remets l'url qui explique bien mieux que moi pourquoi il ne faut
*pas* utiliser un Array() dans ce cas précis puisque tu insistes dans
cette direction qui est fausse, et même pire que fausse, c'est la
direction à ne *pas* prendre :
http://www.andrewdupont.net/2006/05/18/javascript-associative-arrays-considered-harmful/

Ce qu'il a besoin n'est pas un tableau au sens Array() du terme
javascript mais bien un Object().

> 2) La question de l'OP était : existe-t-il un moyen de parcourir un Array
> qui n'est pas 'dense' (qui ne possède pas une valeur pour chaque indice
> inférieur à sa propriété length) ?
>
> La réponse est oui, for(p in o) qui énumérera en p les propriétés
> énumérables définies de l'objet o.

Oui, ai-je proposé qqchose de différents ?
Et comme tu le dis - l'objet o - alors pourquoi aller utiliser un
Array() quand on parle d'Object() ? On retombe sur le problème
d'utiliser un type incompatible avec le besoin.

var x = new Boolean();
x[0] = 'foo';
x[10] = 'bar';
x[20] = 'foobar';

for ( var i in x )
{
alert(i);
}

Ca donne : 0 puis 10 puis 20

Est-ce une raison pour autant d'aller utiliser un Boolean() ? non !

> Ceci n'est pas propre aux Arrays mais
> à tous les objets JS. Ça présente l'avantage pour les Arrays de ne donner
> que les "indices" pour lesquels une valeur est définie. Il donnera
> également
> les autres propriétés qu'on aura pu ajouter à l'objet Array... Se servir
> dans les Arrays des méthodes et opérateurs définis pour les Objects c'est
> prévu. Et ce n'est pas un miracle, c'est de la programmation orientée
> objet -- enfin, tu dois le savoir.

Ah, et depuis quand javascript est orienté objet ? C'est un langage
prototypé, pas du tout objet dans le sens OOP qu'on peut trouver en php
par exemple. Faire l'amalgamme n'est pas aider le lecteur.

> 3) Sur l'utilisation de l'objet global du navigateur : window.
> Tu prétends que
> function remplir() {window.mesDonnees = 'foo';}
> est 'mieux' que
> function remplir() {mesDonnees = 'foo';}

Non, relis mieux au lieu de survoler, j'ai jamais dit que c'était
'mieux', j'ai dit que c'était pas lui rendre service que de lui donner
juste ça comme prétendue "solution". Merci de ne *pas* m'attribuer des
paroles que je n'ai *pas* dites.

> Je ne te suis pas là-dessus. Si une variable est affectée d'une valeur
> dans une fonction et qu'elle n'a pas été déclarée auparavant *dans la
> fonction* c'est qu'elle est appartient à un contexte d'exécution
> 'supérieur'
> voire, /in fine/, au niveau global. La bonne utilisation de la portée
> des variables vient avec la longueur et la complexité des scripts.

Non, la bonne utilisation de la portée des variables vient avec la
rigueur dans la façon d'écrire le code, faire un peu n'importe quoi en
espérant que ça marche, c'est pas comme ça que javascript sera perçu
autrement que comme un langage "gadget".

> L'intérêt d'une écriture comme window.mesDonnees est à mon sens davantage
> de permettre de tester l'existence d'une variable mesDonnees et non de la
> définir...

Je rappelle qu'on a pas la moitié des informations nécessaires pour
déterminer ce que l'OP veut faire ni comment il compte s'y prendre. Sous
prétexte que je n'ai pas voulu perturber l'OP dans ma réponse initiale
tu me prètes des intentions qui ne sont pas les miennes. Tu t'obstines à
interpréter ce que je dit de travers, tant pis. Je remarque que quand
c'est à ton sens ca semble évidemment être la solution universelle à
retenir. Ok, message reçu et évidemment immédiatement ignoré.

> 4) Ce que tu appelles "notation courte" versus "notations d'un âge
> antidéluvien" (quel argument !)

Lol, comme si c'était le seul "argument" que j'avais énoncé. Et quand tu
me demandes les différences et que je réponds "presque aucune". Est-ce
que tu comprends autre chose ? Encore une fois, tant pis.

> Pour ces notations abrégées de l'initialisation d'un Array ou Object,
> la norme ECMA262 emploie l'expression Array Initialiser :

Oui, chapitre 11.1.4 et appendice A.3, où la norme parle d'expression.

<snip>

> Dans un cas on fait appel explicitement au constructeur, dans l'autre
> c'est implicite.

Et ? Si je te suis bien et en appliquant ton raisonnement (explicite vs
implicite) à tous les types existants en javascript, tu prétends que

var x = new String('foo');

serait à conseiller au dépend de

var x = 'foo';

Les deux existent, alors pourquoi prétendre que pour le type tableau
(Array) la notation courte est à proscrire. J'ai juste énoncé le fait
que ça existait, pas que c'était préférable, simplement que ça existait.

> Tu peux donc trouver cela très pratique mais ce n'est qu'une facilité
> d'écriture et n'est pas particulièrement à recommander. On se sert de
> l'un ou l'autre selon ses besoins et préférences -- et ce n'est pas
> parce qu'un script est abscons qu'il est forcément 'mieux'.

Encore une fois, tu m'as lu de travers et tu m'attribues des paroles qui
ne sont *pas*, n'ont jamais et ne seront jamais les miennes.

J'ai jamais dit 'mieux' ni recommandé de l'utiliser, relis moi *mieux*,
j'ai dit :

<cite>


new Array() est transformable à volonté par []

</cite>

Ce qui sous entend bien qu'on peut se servir de l'un ou de l'autre selon
ses besoins et préférences. Et ce n'est pas être abscons que d'indiquer
que ça existe, d'autant plus que la norme, toujours chapitre 11.1.4,
indique bien que la notation est valide. D'autant que tu prétends que ce
n'est pas à recommander, alors je vais te retourner la question. Tu sors
ça d'où que c'est pas recommandé ?

> Laurent vilday a écrit :
>> Javascript est déjà suffisemment mal compris pour ne pas indiquer de
>> mauvaises "solutions" comme tu viens de le faire dans ton message.
>
> Ça s'appelle une attaque ad hominem ? Ou alors tu es *vraiment* persuadé
> de détenir la vérité sur le bon usage du Javascript ?

Lol, je persiste et signe. Dans ton message tu disais :

<cite>


Cela suffit et fonctionne pour un Array.

</cite>

C'est faux, archi faux et absolument pas à préconiser pour le besoin de
l'OP. Donc oui, merci de ne pas indiquer de mauvaises "solutions" comme
tu viens *encore* une fois de le faire, ceci afin de permettre aux
lecteurs de fclj de ne pas enregistrer et reproduire des erreurs dans
leurs developpements.

Pour finir sur le sujet, saches que non, je suis loin d'être persuadé de
détenir une quelconque vérité sur le bon usage de javascript, mais je
suis absolument convaincu du fait que tu ne la détiens pas. Considère ça
comme une attaque ad hominem si ça te chante, et profites en pour relire
la réponse que tu avais faite à mon message, réponse où tu avais
commencé les hostilités. Message ou je te rappelle j'ai donné la
solution adéquate alors que tu donnes la *mauvaise* "solution" !

Détiendrais-tu la vérité sur le bon usage du Javascript ?

--
laurent

Laurent vilday

unread,
Sep 5, 2006, 6:56:55 AM9/5/06
to
YD a écrit :

> 4) Ce que tu appelles "notation courte" versus "notations d'un âge
> antidéluvien" (quel argument !)
>
> Pour ces notations abrégées de l'initialisation d'un Array ou Object,
> la norme ECMA262 emploie l'expression Array Initialiser :
> "An array initialiser is an expression describing the initialisation
> of an Array object, written in a form of a literal."
> Dans ce cas la première étape que doit faire le moteur JS, face à ce
> type d'écriture :
> "1. Create a new array as if by the expression new Array()."
> Dans un cas on fait appel explicitement au constructeur, dans l'autre
> c'est implicite.
> Tu peux donc trouver cela très pratique mais ce n'est qu'une facilité
> d'écriture et n'est pas particulièrement à recommander.

Et bien, il suffit de vérifier pour se persuader du contraire :

http://mokhet.com/tests/benchArray.html

resultats (A) pour new Array()
resultats (B) pour []

IE6
(A) : 141 - 156 - 141 - 141 - 141
(B) : 110 - 110 - 110 - 109 - 110
moyenne (A) : 144
moyenne (B) : 109,8
gagnant : (B)

Fx 1.5.0.6
(A) : 609 - 610 - 625 - 625 - 640
(B) : 609 - 609 - 609 - 594 - 610
moyenne (A) : 621,8
moyenne (B) : 606,2
gagnant : (B)

Opéra 9
(A) : 266 - 234 - 265 - 203 - 234
(B) : 188 - 172 - 172 - 156 - 172
moyenne (A) : 240,4
moyenne (B) : 172
gagnant : (B)

Il semblerait donc que la notation [] soit à *recommander* par rapport à
la notation new Array(), au moins pour ces 3 navigateurs en
environnement windows (pas le courage de tester ni en slackware ni sur
d'autres navigateurs, j'ai assez perdu mon temps avec ça), puisque :
- la notation courte [] va un tantinet plus vite,
- permet une écriture plus concise,
- permet de préremplir les tableaux de façon simplifiée,
- permet même la création de tableaux multidimensionnels ce que ne
permet pas new Array().

Mais je suis d'accord, ce n'est pas sur quelques microsecondes que va se
faire la vrai différence et tout dépend de ce qui tourne en fond de
tache, des extensions, etc.

A la vue des moyennes obtenues, ll n'y a *aucune* raison de ne pas
l'utiliser.

<script type="text/javascript">
var bench =
{
D:0,
T:'',
init:function(T)
{
bench.T = T;
bench.D = (new Date()).valueOf();
},
fin:function()
{
return (new Date()).valueOf() - bench.D;
}
};

var MSG = '';

function b1()
{
bench.init('new Array()');
var X;
for ( var i = 0; i < 100000; i++ )
{
X = new Array();
}
MSG += bench.T + ' : ' + bench.fin() + '<br>';
setTimeout(b2, 50);
}

function b2()
{
bench.init('[]');
var X;
for ( var i = 0; i < 100000; i++ )
{
X = [];
}
MSG += bench.T + ' : ' + bench.fin() + '<br>';
document.getElementById('results').innerHTML = MSG;
}

window.onload = b1;
</script>

<div id="results"></div>

--
laurent

Pierre Goiffon

unread,
Sep 5, 2006, 7:18:46 AM9/5/06
to
Laurent vilday wrote:
> Il semblerait donc que la notation [] soit à *recommander* par rapport à
> la notation new Array(), au moins pour ces 3 navigateurs en
> environnement windows (pas le courage de tester ni en slackware ni sur
> d'autres navigateurs, j'ai assez perdu mon temps avec ça), puisque :
> - la notation courte [] va un tantinet plus vite,
> - permet une écriture plus concise,
> - permet de préremplir les tableaux de façon simplifiée,
> - permet même la création de tableaux multidimensionnels ce que ne
> permet pas new Array().

En effet ça semble assez séduisant d'un point de vue syntaxe
Par contre quid du support ? (je pense en particulier à IE 5 et Safari ?)

Laurent vilday

unread,
Sep 5, 2006, 7:53:58 AM9/5/06
to
Pierre Goiffon a écrit :

De mémoire, la notation courte (literal array) a été introduite en
Javascript 1.2. Je n'ai malheureusement aucun moyen de vérifier mais à
priori IE5 ça devrait pas lui poser de problème, quand à safari, je ne
vois que ASM pour pouvoir nous dire si oui ou non c'est utilisable.
J'aurai tendance à dire que oui mais sans aucune certitude
malheureusement :(

--
laurent

ASM

unread,
Sep 5, 2006, 11:08:23 AM9/5/06
to
Laurent vilday a écrit :

Bon, à mon idée, cette notation courte n'est pas nouvelle nouvelle,
Même sous NC4 c'est OK. C'est dire !

<script type="text/javascript">
var I = [1,'truc','bidule'];
alert(I); // 1,truc,bidule
alert(I[2]); // bidule
</script>

alors si Safari n'y arrive pas ...
y a pu qu'à tirer l'échelle !

Mais que les foules attentives se rassurent :
Safari passe le test ci-dessus

Quant à dire que Array() ne permet pas les tableaux multidimensionnels
...
personne ne m'avait prévenu !
Ce qui est curieux c'est que Array() ne semble pas être au courant de
cette nouveauté.

Laurent vilday

unread,
Sep 5, 2006, 11:49:04 AM9/5/06
to
ASM a écrit :

> Quant à dire que Array() ne permet pas les tableaux multidimensionnels
> ...
> personne ne m'avait prévenu !
> Ce qui est curieux c'est que Array() ne semble pas être au courant de
> cette nouveauté.

Lol, j'étais tellement énervé par tant d'instance de la part de YD sur
des remarques totallement erronnées, que j'en ai oublié des mots :)

Quand je disais :


- permet même la création de tableaux multidimensionnels ce que ne
permet pas new Array().

En fait je pensais :
- permet même /de façon rapide et concise/ la création de tableaux
multidimensionnels ce que ne permet pas /aussi facilement/ new Array().

Ceci pour dire que

var tbl = [[[1,2,3], [2,3,4]], {foo:'bar',bar:'foo'}, [10], [20]];

est bien plus rapide a écrire, et à lire mais ça c'est personnel je
pense, que :

var tbl = new Array();
tbl[0] = new Array();
tbl[0][0] = new Array(1, 2, 3);
tbl[0][1] = new Array(2, 3, 4);
tbl[1] = new Object();
tbl[1].foo = 'bar';
tbl[1].bar = 'foo';
tbl[2] = new Array();
tbl[2][0] = 10;
tbl[3] = new Array()
tbl[3][0] = 20;

Merci Stéphane pour ce rappel qui méritait effectivement une précision.

self note : après s'être relu une dizaine de fois, recommencer et se
relire encore :D

--
laurent

Pierre Goiffon

unread,
Sep 5, 2006, 11:56:03 AM9/5/06
to
ASM wrote:
>>>> - la notation courte [] va un tantinet plus vite,
>>>> - permet une écriture plus concise,
>>>> - permet de préremplir les tableaux de façon simplifiée,
>>>> - permet même la création de tableaux multidimensionnels ce que ne
>>>> permet pas new Array().
>>>
>>> En effet ça semble assez séduisant d'un point de vue syntaxe
>>> Par contre quid du support ? (je pense en particulier à IE 5 et
>>> Safari ?)
>>
>> De mémoire, la notation courte (literal array) a été introduite en
>> Javascript 1.2. Je n'ai malheureusement aucun moyen de vérifier mais à
>> priori IE5 ça devrait pas lui poser de problème, quand à safari, je ne
>> vois que ASM pour pouvoir nous dire si oui ou non c'est utilisable.
>
> Même sous NC4 c'est OK. C'est dire !
(...)

> Safari passe le test ci-dessus

Merci à vous 2 pour toutes ces explications !

YD

unread,
Sep 5, 2006, 5:32:27 PM9/5/06
to
Laurent vilday a écrit :

> YD a écrit :
>> 4) Ce que tu appelles "notation courte" versus "notations d'un âge
>> antidéluvien" (quel argument !)
>> [...]
>> Tu peux donc trouver cela très pratique mais ce n'est qu'une facilité
>> d'écriture et n'est pas particulièrement à recommander.

Je dis bien *pas particulièrement à recommander*.

> Et bien, il suffit de vérifier pour se persuader du contraire :

J'ai refait tes tests tels que puis en modifiant les créations
d'Array (en les initialisant avec quelques valeurs pour voir).
Même chose dans les deux cas : résultats comparables dans les
mêmes proportions pour IE6 et Opera 9 mais avec Fx 2.0b2, les
résultats sont inverses (plus longs avec l'écriture condensée)

new Array() 4082 (de 4 à 5 fois plus long que IE et Op)
[] 4711 (temps moyens sur 5 essais)

J'ai rajouté une troisième écriture : Array() (sans new). C'est
un peu plus long à traiter que new Array() pour IE et Fx, mais
très légèrement plus rapide avec Opera.

Les fonctions comme je les ai modifiées sont à la fin du post.
----
Puisque les Array ont l'air d'intéresser...

a) Une bizarrerie remarquée (bug ?). Quand on crée un Array non
densément peuplé -- ce qui se fait très bien avec la notation courte
mais pas avec le constructeur -- comme par exemple :

var t = ['A',,,'B'];
for (var i in t) document.write(i + ' -> ' + t[i] + '<br>');

On obtient le résultat escompté avec IE et Op :
0 -> A
3 -> B

mais Firefox 2.0b2 répond
0 -> A
1 -> undefined
2 -> undefined
3 -> B

À tester également [,,,,] qui retourne un résultat différent dans ces
3 navigateurs !

b) Il est possible d'écrire presque la même chose avec les notations
constructeur et condensées sauf pour
- un Array non densément peuplé (impossible d'écrire new Array(1,,,3))
- un Array à un seul élément comme [5], car new Array(5) crée un tableau
dont la propriété length est 5 mais qui ne contient aucun élément défini :
for ... in ... ne retourne rien.

Par exemple :
var tbl = [[[1,2,3], [2,3,4]], {foo:'bar',bar:'foo'}];

peut s'écrire :

var tbl = new Array(
new Array(
new Array(1,2,3),
new Array(2,3,4)),
new function()
{this.foo='bar'; this.bar='foo';});

C'est certes moins élégant mais pas moins possible et tout aussi
lisible.

----
Les fonctions de test modifiées

function b1()
{
bench.init('new Array()');

var X, Y;
for ( var i = 0; i < 50000; i++ )
{
X = new Array("a","b","c",123,456,7890);
Y=new Array(new Array(), new Array());


}
MSG += bench.T + ' : ' + bench.fin() + '<br>';
setTimeout(b2, 50);
}

function b2()
{
bench.init('Array()');
var X, Y;
for ( var i = 0; i < 50000; i++ )
{
X = Array("a","b","c",123,456,7890);
Y= Array( Array(), Array());


}
MSG += bench.T + ' : ' + bench.fin() + '<br>';

setTimeout(b3, 50);
}

function b3()
{
bench.init('[]');
var X, Y;
for ( var i = 0; i < 50000; i++ )
{
X = ["a","b","c",123,456,7890];
Y=[[],[]];


}
MSG += bench.T + ' : ' + bench.fin() + '<br>';
document.getElementById('results').innerHTML = MSG;
}

--
Y.D.

YD

unread,
Sep 5, 2006, 5:38:24 PM9/5/06
to
J'interviens encore une fois sur le sujet...

Laurent vilday a écrit :


> YD a écrit :
>> Je ne vais pas répondre dans le fil, ça serait indigeste, mais reprendre
>> quelques points et développer.
>
> Mouais évidemment, ça va aider à comprendre c'est certain. D'un autre
> côté, ça va te permettre de me préter des paroles qui ne sont pas les
> miennes, belle technique.

Mais tu es infect ! Quels propos je t'ai indûment prêtés ? le 'mieux' ?
Je n'avais pas écrit "mieux".

>> 1) L'OP devait-il utiliser un Array ?
>
> Non !

> [...] Toute la problématique est résumé avec ces 3 mots :
> "pas nécessairement consécutifs"

Un Array n'a pas forcément une valeur pour chaque indice, par définition.
C'est bizarre mais c'est propre au JS.

>> Par ailleurs on ne sait pas quelles propriétés spécifiques aux Arrays
>> sont utilisées. S'il n'y en a aucune, il est alors possible d'utiliser
>> des Objects mais pourquoi pas un Array qui permettra de connaître très
>> vite le plus grand identifiant numérique utilisé (mesDonnees.length-1).
>
> Non, ce n'est pas consécutifs, d'après ce qu'il dit il a potentiellement
> ceci :
>
> mesDonnees[0] = [];
> mesDonnees[1] = [];
> mesDonnees[31] = [];
> mesDonnees[20] = [];
> mesDonnees[8] = [];
>
> alert(mesDonnees.length - 1);
> // 31
>
> 31 ?!?! Ce n'est pas vrai, tout simplement.

Eh bien c'est le plus grand identifiant utilisé. Qu'est-ce qui n'est pas
vrai mon garçon ?

> Je remets l'url qui explique bien mieux que moi pourquoi il ne faut
> *pas* utiliser un Array() dans ce cas précis puisque tu insistes dans
> cette direction qui est fausse, et même pire que fausse, c'est la
> direction à ne *pas* prendre :
> http://www.andrewdupont.net/2006/05/18/javascript-associative-arrays-considered-harmful/

J'y avais jeté un coup d'oeil et sur les commentaires aussi. Le moins
qu'on puisse dire c'est que l'article ne fait pas l'unanimité.

> Ce qu'il a besoin n'est pas un tableau au sens Array() du terme
> javascript mais bien un Object().

Je l'ai déjà écrit, je ne sais pas s'il utilise d'autres propriétés des Array.

>> 2) La question de l'OP était : existe-t-il un moyen de parcourir un Array
>> qui n'est pas 'dense' (qui ne possède pas une valeur pour chaque indice
>> inférieur à sa propriété length) ?
>>
>> La réponse est oui, for(p in o) qui énumérera en p les propriétés
>> énumérables définies de l'objet o.
>
> Oui, ai-je proposé qqchose de différents ?

Je ne t'ai pas contredit sur ce point. Ce que tu n'as pas dit, et ce
pourquoi je suis intervenu, est que cela marche bien pour un Array et
répond exactement à la question clairement énoncée de l'OP : comment
énumérer les indices non consécutifs d'un Array.

> Et comme tu le dis - l'objet o - alors pourquoi aller utiliser un
> Array() quand on parle d'Object() ? On retombe sur le problème
> d'utiliser un type incompatible avec le besoin.

Quel type incompatible ? Un Array est un objet JS avec des commodités
particulières.

> var x = new Boolean();
> x[0] = 'foo'; x[10] = 'bar'; x[20] = 'foobar';
> for ( var i in x ) alert(i);
> Ca donne : 0 puis 10 puis 20
>
> Est-ce une raison pour autant d'aller utiliser un Boolean() ? non !

Sauf si ça me chante car c'est licite et syntaxiquement correct en JS.

>> Ceci n'est pas propre aux Arrays mais
>> à tous les objets JS. Ça présente l'avantage pour les Arrays de ne donner
>> que les "indices" pour lesquels une valeur est définie. Il donnera
>> également
>> les autres propriétés qu'on aura pu ajouter à l'objet Array... Se servir
>> dans les Arrays des méthodes et opérateurs définis pour les Objects c'est
>> prévu. Et ce n'est pas un miracle, c'est de la programmation orientée
>> objet -- enfin, tu dois le savoir.
>
> Ah, et depuis quand javascript est orienté objet ?

"ECMAScript is an object-oriented programming language for performing
computations and manipulating computational objects within a host environment."
(ECMA 262 p. 1)

> C'est un langage
> prototypé, pas du tout objet dans le sens OOP qu'on peut trouver en php
> par exemple. Faire l'amalgamme n'est pas aider le lecteur.

Pour le coup, je ne suis pas sûr que c'est moi qui dise des inepties...

>> 3) [...]
Tout ce que tu as dit là n'ajoute rien au débat. C'est attaque personnelle
sur attaque personnelle. Aucun intérêt.

>
>> 4) Ce que tu appelles "notation courte" versus "notations d'un âge
>> antidéluvien" (quel argument !)
>
> Lol, comme si c'était le seul "argument" que j'avais énoncé. Et quand tu
> me demandes les différences et que je réponds "presque aucune". Est-ce
> que tu comprends autre chose ? Encore une fois, tant pis.
>
>> Pour ces notations abrégées de l'initialisation d'un Array ou Object,
>> la norme ECMA262 emploie l'expression Array Initialiser :
>
> Oui, chapitre 11.1.4 et appendice A.3, où la norme parle d'expression.
>
> <snip>
>
>> Dans un cas on fait appel explicitement au constructeur, dans l'autre
>> c'est implicite.
>
> Et ? Si je te suis bien et en appliquant ton raisonnement (explicite vs
> implicite) à tous les types existants en javascript, tu prétends que
>
> var x = new String('foo');
>
> serait à conseiller au dépend de
>
> var x = 'foo';

Non, Môssieu. Dans x='foo', 'foo' est une valeur primitive du langage et x
une référence vers cette valeur. Alors que dans x = new String('foo'),
x est un objet !

Array par contre ne fait pas partie des types primitifs du langage.

Ceci dit, si tu avais essayé de comprendre, je disais que ces écritures sont
équivalentes. En bref c'est plus un choix esthétique, des habitudes (un
programmeur Java va certainement préférer utiliser les constructeurs alors
qu'un programmeur PERL les formes condensées) qui vont dicter la
préférence la plupart du temps.

> Les deux existent, alors pourquoi prétendre que pour le type tableau
> (Array) la notation courte est à proscrire. J'ai juste énoncé le fait
> que ça existait, pas que c'était préférable, simplement que ça existait.

Je n'avais pas compris le sens de antédiluvien alors (pardon tu as écrit
antidéluvien, je ne voulais pas déformer tes propos).

>> Tu peux donc trouver cela très pratique mais ce n'est qu'une facilité
>> d'écriture et n'est pas particulièrement à recommander. On se sert de
>> l'un ou l'autre selon ses besoins et préférences -- et ce n'est pas
>> parce qu'un script est abscons qu'il est forcément 'mieux'.
>
> Encore une fois, tu m'as lu de travers et tu m'attribues des paroles qui
> ne sont *pas*, n'ont jamais et ne seront jamais les miennes.
>
> J'ai jamais dit 'mieux' ni recommandé de l'utiliser, relis moi *mieux*,
> j'ai dit :
>
> <cite>
> new Array() est transformable à volonté par []
> </cite>
>
> Ce qui sous entend bien qu'on peut se servir de l'un ou de l'autre selon
> ses besoins et préférences. Et ce n'est pas être abscons que d'indiquer
> que ça existe, d'autant plus que la norme, toujours chapitre 11.1.4,
> indique bien que la notation est valide. D'autant que tu prétends que ce
> n'est pas à recommander, alors je vais te retourner la question. Tu sors
> ça d'où que c'est pas recommandé ?

Fais la nuance entre
"pas à recommander" (ce que tu me fais dire)
et
"pas particulièrement à recommander" (ce que j'ai écrit).

> [...]

> Pour finir sur le sujet, saches que non, je suis loin d'être persuadé de
> détenir une quelconque vérité sur le bon usage de javascript, mais je
> suis absolument convaincu du fait que tu ne la détiens pas.

Bon, on est d'accord sur ces deux points.

> Considère ça
> comme une attaque ad hominem si ça te chante, et profites en pour relire
> la réponse que tu avais faite à mon message, réponse où tu avais
> commencé les hostilités.

Exact, car je trouve que tu aurais pu répondre plus simplement : commencer (et
non finir) par la solution du for...in, ajouter ensuite d'autres
considérations sur l'utilité de l'Array, sur les questions de style, etc. et
préciser que le script n'était pas forcément à réécrire car les [] sont un cas
particulier de {} et que ce qui marche pour les {} marche aussi pour les [] et
que cela était syntaxiquement correct, même si tu avais des réserves à apporter
sur les Arrays non denses).

Pour moi, encore quelques remarques ineptes sur les Arrays (ton test, autre
message) et fin du fil.


--
Y.D.

Laurent vilday

unread,
Sep 5, 2006, 6:33:09 PM9/5/06
to
YD a écrit :

> J'interviens encore une fois sur le sujet...

T'aurais mieux fait de t'abstenir, tu continues a raconter n'importe
quoi, à mélanger mes dires et à être d'une mauvaise foi incroyable. A
l'avenir oublies moi et contentes toi de donner des solutions *valides*
dans les temps au lieu de venir avec tes gros sabots raconter des
inepties énormes en prétendant détenir la solution alors que la solution
correcte a déjà été fournie et appréciée à sa juste valeur par l'OP !

Adieu.

--
laurent

ASM

unread,
Sep 5, 2006, 7:24:03 PM9/5/06
to
Laurent vilday a écrit :

> YD a écrit :
>> J'interviens encore une fois sur le sujet...
>
> T'aurais mieux fait de t'abstenir,
[...]
> Adieu.

Y a pas, vous êtes trop bonnards :-)
On se croirait sur comp.lang.javascript
C'est très distrayant bien que de temps en temps instructif.
J'espère vous revoir très bientôt.

ASM

unread,
Sep 6, 2006, 5:36:52 AM9/6/06
to
Laurent vilday a écrit :

> T'aurais mieux fait de

Je suppose que tu as lu :
<1157523492....@m73g2000cwd.googlegroups.com>>

ATH

BertrandB

unread,
Sep 6, 2006, 3:29:14 PM9/6/06
to
YD a écrit :

> a) Une bizarrerie remarquée (bug ?). Quand on crée un Array non
> densément peuplé -- ce qui se fait très bien avec la notation courte
> mais pas avec le constructeur -- comme par exemple :
>
> var t = ['A',,,'B'];
> for (var i in t) document.write(i + ' -> ' + t[i] + '<br>');
>
> On obtient le résultat escompté avec IE et Op :
> 0 -> A
> 3 -> B
>
> mais Firefox 2.0b2 répond
> 0 -> A
> 1 -> undefined
> 2 -> undefined
> 3 -> B

Sémantiquement firefox est dans le vrai ["A",,,"B"]moi je lis un tableau
de 4 éléments dony le 2ème et le 3ème n'ont pas été définis.

Un tableau creux je l'écrirais !
t=new Array();
t[0]="A";
t[3]="B";
for (var i in t) print(i + ' -> ' + t[i] + '<br>');
Et là firefox répond
0 -> A<br>
3 -> B<br>
Mais dans quel cas je préférerais une notation de type dictionnaire.
t={0:'A',3:'B'};
for (var i in t) print(i + ' -> ' + t[i] + '<br>');
Et firefox répond
0 -> A<br>
3 -> B<br>

YD

unread,
Sep 7, 2006, 2:56:04 AM9/7/06
to
BertrandB a écrit :

> YD a écrit :
>
>> a) Une bizarrerie remarquée (bug ?). Quand on crée un Array
>> var t = ['A',,,'B'];
>>
>> On obtient avec IE et Op :

>> 0 -> A
>> 3 -> B
>>
>> mais Firefox 2.0b2 répond
>> 0 -> A
>> 1 -> undefined
>> 2 -> undefined
>> 3 -> B
>
> Sémantiquement firefox est dans le vrai

La question n'est-elle pas plutôt de savoir ce que prescrit la
norme (ECMA 262 3e éd.) ou si elle prévoit une latitude aux
différentes implémentations ? En l'occurrence, si j'ai bien
compris, Fx n'est pas "compliant" sur ce point.

> ["A",,,"B"]moi je lis un tableau
> de 4 éléments dony le 2ème et le 3ème n'ont pas été définis.

Et bien moi je lis (après mise en oeuvre de l'algo de la norme)
un Array dont length est 4 et dont les propriétés nommées '0'
et '3' correspondent aux valeurs "A" et "B". L'Array en question
ne possède pas de 2e et 3e éléments. Si je veux obtenir la même
chose que Fx je devrais écrire :
var t=['A',undefined,undefined,'B'];
Là, ne créant pas d'élision (la virgule au début ou après une autre),
je force la création des propriétés '1' et '2' (ce que JScript -- IE
donc -- ne fait pas, ignorant les undefined...)

> Un tableau creux je l'écrirais !
> t=new Array();
> t[0]="A";
> t[3]="B";

Les deux écritures *doivent* produire le même résultat.

> Mais dans quel cas je préférerais une notation de type dictionnaire.
> t={0:'A',3:'B'};

Ce n'est pas une question de notation. Ici tu crées un Object et
non un Array (qui est dérivé de Object). Il s'agit de savoir quels
sont ses besoins. Si on n'utilise pas les propriétés des Arrays (les
nombreuses fonctions du prototype : join, concat, splice...) il est
effectivement sans intérêt d'utiliser un Array, puisqu'on ne se sert
alors que des propriétés dont il hérite d'Object !

--
Y.D.

ASM

unread,
Sep 7, 2006, 5:02:51 AM9/7/06
to
YD a écrit :

>
> Les deux écritures *doivent* produire le même résultat.

proposition de petit test :

t=new Array();
t[0]="A";
t[3]="B";

var tbl = '<br>Array() avec length ==> ';
for(var i=0; i<t.length; i++) tbl += t[i]+' | ';
document.write(tbl);
var tbl = '<br>Array() avec in ==> ';
for(var i in t) tbl += t[i]+' | ';
document.write(tbl+'<br>');

t = ['A',,,'B'];

var tbl = '<br>[...] avec length ==> ';
for(var i=0; i<t.length; i++) tbl += t[i]+' | ';
document.write(tbl);
var tbl = '<br>[...] avec in ==> ';
for(var i in t) tbl += t[i]+' | ';
document.write(tbl+'<br>');


Résultats chez moi :

= IE 5.2 Mac = Safari 1.3.2 = Opera 9 = iCab 3 =
Array() avec length ==> A | undefined | undefined | B |
Array() avec in ==> A | B |
[...] avec length ==> A | undefined | undefined | B |
[...] avec in ==> A | B |

= Fx 1.5.0.6 =
Array() avec length ==> A | undefined | undefined | B |
Array() avec in ==> A | B |
[...] avec length ==> A | undefined | undefined | B |
[...] avec in ==> A | undefined | undefined | B |


Lequel de ces navigateurs a un bug ?

BertrandB

unread,
Sep 7, 2006, 4:52:01 PM9/7/06
to
YD a écrit :

> Et bien moi je lis (après mise en oeuvre de l'algo de la norme)
> un Array dont length est 4 et dont les propriétés nommées '0'
> et '3' correspondent aux valeurs "A" et "B". L'Array en question
> ne possède pas de 2e et 3e éléments.

Et bien ça me choque qu'un tableau ait des propriété et non pas des
'cases' ....Et sinon tu viens le dire aussi il est de 4 éléments dont
seulement deux ont une valeur définie.
Comme quoi, au delà des algorithme et des implémentations physiques il
faut bien se mettre d'accord sur le sens.

Euh "les propriétés ... correspondent aux valeurs" en d'autres forum
(python) ce genre d'approximation se fait flinguer. La tournure est mal
venue car elle confond le contenant et le contenu.

Cordialement.

YD

unread,
Sep 7, 2006, 5:14:15 PM9/7/06
to
Désolé Stéphane, je ne vais pas réussir à être bref !

ASM a écrit :


> YD a écrit :
>> Les deux écritures *doivent* produire le même résultat.
>
> proposition de petit test :
>

> [...]


>
> Résultats chez moi :
>
> = IE 5.2 Mac = Safari 1.3.2 = Opera 9 = iCab 3 =

> [...] avec in ==> A | B |
>
> = Fx 1.5.0.6 =

> [...] avec in ==> A | undefined | undefined | B |
>
> Lequel de ces navigateurs a un bug ?

Il me semble que Firefox ne devrait pas créer les propriétés
'1' et '2'. Si j'ai bien compris l'algorithme (p. 40 et 41 de
la norme ECMA 262 3e éd.) les éléments élidés (une virgule au
début ou deux virgules consécutives) modifient la propriété
length de l'Array mais aucune nouvelle propriété n'est créée.

Quand le JS rencontre ['A',,,'B'] :
- Il évalue 'A' et crée une Array contenant l'élément nommé
'0' avec la valeur 'A',length 1.
- Ensuite il y a une élision (2 virgules se suivent), la
valeur de length est augmentée de 1.
- Encore une élision, on augmente de 1 length.
- Enfin 'B', on ajoute à l'Array une propriété nommée
comme la valeur de length, donc 3, et avec la valeur 'B'.

Au final on se retrouve avec une Array de length 4 et deux
éléments définis et effectivement créés '0' et '3'. Donc
l'énumération des propriétés énumérables avec for ... in
ne doit pas faire ressortir '1' -> undefined et
'2' -> undefined puisque ces propriétés ne devraient pas
avoir été créées.

Si on veut obtenir A | undefined | undefined | B | il faut
le déclarer explicitement en écrivant :
['A',undefined,undefined,'B']

Mais si l'on procède ainsi c'est IE/Win qui cette fois déraille,
en faisant comme si on avait écrit ['A',,'B'] !

--
Y.D.


YD

unread,
Sep 7, 2006, 5:56:26 PM9/7/06
to
BertrandB a écrit :

> YD a écrit :
>
>> Et bien moi je lis (après mise en oeuvre de l'algo de la norme)
>> un Array dont length est 4 et dont les propriétés nommées '0'
>> et '3' correspondent aux valeurs "A" et "B". L'Array en question
>> ne possède pas de 2e et 3e éléments.
>
> Et bien ça me choque qu'un tableau ait des propriété et non pas des
> 'cases' ....

C'est que tu penses à un tableau comme une structure de données, comme
en C, sans doute. Ce que n'est absolument pas un Array en javascript.
C'est un descendant de l'objet Object. Pour s'en convaincre :

Object.prototype.tag='$$$';
var a=[0,,,,1];
for (var i in a)
document.writeln('a[' + i + '] = ' + a[i]);

> Et sinon tu viens le dire aussi il est de 4 éléments dont
> seulement deux ont une valeur définie.

Jamais dit ça ! J'ai dit length est 4, c.-à-d. sa propriété nommée
length contient la valeur 4 !

> Comme quoi, au delà des algorithme et des implémentations physiques il
> faut bien se mettre d'accord sur le sens.

Et quand on utilise un Array en javascript comprendre qu'on n'a pas du
tout un tableau tel qu'on l'entend en C, en Perl, etc.

> Euh "les propriétés ... correspondent aux valeurs" en d'autres forum
> (python) ce genre d'approximation se fait flinguer. La tournure est mal
> venue car elle confond le contenant et le contenu.

C'est un forum difficile aussi celui-ci, même s'il y a peu de contributeurs
-- y en a un qui m'a flamé et boude maintenant ! En tout cas je te remercie
du ton que tu utilises alors que, visiblement, on n'est pas d'accord.

C'est vrai que c'était mal tourné et la phrase suivante également. C'était
une approximation. Ce n'est pas facile de rester clair en parlant technique.
J'aurais dû écrire en toute rigueur :
...et dont les propriétés nommées '0' et '3' contiennent respectivement
les valeurs "A" et "B". Cet objet Array ne possède pas de propriétés
nommées '1' et '2'.

> Cordialement.

De même.

--
Y.D.

BertrandB

unread,
Sep 8, 2006, 2:21:13 PM9/8/06
to
YD a écrit :

s' ....
>
> C'est que tu penses à un tableau comme une structure de données, comme
> en C, sans doute.

Non non ... je fait référence au monde réel pas à un langage précis. Le
fait que le "array" soit un object qui est lui même un dictionnaire ...
c'est de l'implémentation.

0 new messages