Lors de la lecture de cet article publié sur dzone j'ai trouvé un extrait de code de JavaScript initialement posté sur Twitter par Marcus Lagergren.
Le code suivant apparemment affiche la chaîne de caractères "fail"
(![]+[])[+[]]+(![]+[])[+!+[]]+([![]]+[][[]])[+!+[]+[+[]]]+(![]+[])[!+[]+!+[]];
Cela implique implicitement le type coulée et j'essaie de comprendre exactement comment cette ligne est interprété.
J'ai isolé de chaque personnage
-
(![]+[])[+[]]
tirages"f"
-
(![]+[])[+!+[]]
tirages"a"
-
([![]]+[][[]])[+!+[]+[+[]]]
tirages"i"
-
(![]+[])[!+[]+!+[]]
tirages"l"
J'ai aussi réussi à briser les expressions qui reviennent chaque lettre en dehors de "i"
lettre "f"
![]
un tableau vide est un Objet, qui, selon ECMAScript documentation, point 9.2 évalue true
après conversion en boolean
donc c'est false
false+[]
par Point 11.6.1 les deux arguments de la binaire +
opérateur se converti en Chaîne de caractères, par conséquent, nous obtenons "false"+""
, qui évalue "false"
+[]
unaire opérateur plus provoque une ToNumber
conversion suivie par un ToPrimitive
de conversion si l'argument est une Object
. Le résultat de la conversion est déterminée par l'appel de la [[DefaultValue]]
méthode interne de l'objet. Dans le cas d'un tableau vide, la valeur par défaut est 0
.
(ECMAScript de la Documentation, de sections: 11.4.6, 9.3, 9.1 )
"false"[0]
nous sommes accéder au caractère à l'indice 0
, d'où l' "f"
lettre "a"
Même histoire, la seule différence ici sont des conversions supplémentaires dans la partie entre crochets (ce qui donne un nombre de point à un autre caractère dans la chaîne "false"
), déclenchée par l'utilisation de unaire +
et !
opérateurs.
+[]
évalue 0
, comme expliqué ci-dessus.
!0
évalue true
tel que défini à l'Article 9.2 et à l'Article 11.4.9. Tout d'abord, 0
, est converti en une valeur de type boolean false
puis l'opérateur inverse de la valeur.
+true
nouveau, la unaires plus déclenche une ToNumber
de conversion, qui renvoie un 1
pour les binaires true
(Section 11.4.6 et 9.3)
"false"[1]
renvoie le deuxième caractère de la chaîne, qui est "a"
la lettre "l"
!+[]
évalue true
comme expliqué ci-dessus
true+true
en utilisant le binaire +
sur les primitives déclenche une ToNumber
de conversion. En cas de vrai, son résultat est 1
et 1+1
équivaut 2
"false"[2]
- auto-explicatif
lettre "i"
Ce qui me laisse perplexe, c'est la lettre "i"
. Je peux voir que la deuxième partie (entre crochets) renvoie la chaîne de caractères "10"
et que la première partie (entre parenthèses) renvoie "falseundefined"
mais je ne peux pas faire des têtes ou queues de comment cela se passe. Quelqu'un pourrait-il expliquer étape par étape? Surtout la magie qui se passe avec les crochets? (tableaux et d'accès au tableau)
Si possible, j'aimerais que chaque étape pour contenir un lien vers le sous-jacent ECMAScript règles.
Ce que je trouve le plus cryptique est cette partie: [][[]]