Avec des expressions JavaScript comme :
a = b = 4; c[i] = c[++i] = 4;
les opérateurs d'affectation sont évalués de droite à gauche, mais chaque opérande est d'abord évalué distinctement de gauche à droite.
Ainsi, dans la chronologie de l'exécution, les opérandes sont individuellement évalués à partir de celui de gauche, avant d'être chaînés à partir de la droite via l'opérateur d'affectation. L'expression est alors globalement évaluée à rebours des évaluations individuelles.
La chaîne des opérateurs d’affectation
Chronologie des exécutions opérande par opérande
Pour constater que l'évaluation de chaque expression d'opérande se fait dans le sens inverse de la chaîne des affectations (L’associativité de l’opérateur d’affectation est de droite à gauche
), lisons le résultat du test suivant :
var alpha = new Array(3), beta = new Array(3), gamma = new Array(3), index = -1; alpha[++index] = beta[++index] = gamma[++index] = index; console.log("alpha :",alpha,"beta :",beta,"gamma :",gamma);=>
"alpha" : [2, undefined, undefined] "beta" : [undefined, 2, undefined] "gamma" : [undefined, undefined, 2]
C'est le premier élément du tableau 'alpha' qui est affecté. Ainsi, l'incrémentation initiale de la variable 'index' n'est pas due à l'expression 'gamma[++index]', mais à l'expression 'alpha[++index]', en allant de gauche à droite.
Ça manifeste que les opérandes sont évalués distinctement de gauche à droite, avant l'action de droite à gauche des opérateurs d'affectation.
Note sur les notions d'associativité
Sans confusion avec la notion d'associativité en algèbre, dans laquelle ces deux formules-ci sont équivalentes :
opérande opérateur (opérande opérateur opérande) (opérande opérateur opérande) opérateur opérande
Mais entendre ici "associativité" comme le chaînage déterminé - de droite à gauche - de la suite des affectations, dit en l'occurrence et autrement :
alpha[++index] = (beta[++index] = (gamma[++index] = index));
Cf. page 65 (id.) : L’associativité d’un opérateur spécifie l’ordre selon lequel les opérations ayant la même priorité sont effectuées.
(*) 4.7.7 Order of Evaluation
"Operator precedence and associativity specify the order in which operations are performed in a complex expression, but they do not specify the order in which the subexpressions are evaluated. JavaScript always evaluates expressions in strictly left- to-right order. In the expression w=x+y*z, for example, the subexpression w is evaluated first, followed by x, y, and z. Then the values of y and z are multiplied, added to the value of x, and assigned to the variable or property specified by expression w. Adding parentheses to the expressions can change the relative order of the multiplication, addition, and assignment, but not the left-to-right order of evaluation.
Order of evaluation only makes a difference if any of the expressions being evaluated has side effects that affect the value of another expression. If expression x increments a variable that is used by expression z, then the fact that x is evaluated before z is important."
Aucun commentaire:
Enregistrer un commentaire