Parece que no puedo entender la primera parte de este código (+ =) en combinación con el operador ternario.
h.className += h.className ? ' error' : 'error'
La forma en que creo que funciona este código es la siguiente:
h.className = h.className + h.className ? ' error' : 'error'
Pero eso no es correcto porque da un error en mi consola.
Entonces, mi pregunta es ¿cómo debo interpretar este código correctamente?
h.className += ' error'
, también deja un espacio en blanco al comienzo de la cadena si inicialmente estaba vacío. Creo que el objetivo de la operación ternaria es producir una cuerda de aspecto limpio.Piénsalo de esta manera:
La forma en que se ejecuta la declaración es básicamente la siguiente:
<expression>
evalúa como verdadero o se evalúa como falso?<expression>
evalúa como verdadero, entonces<true clause>
se asigna el valor de<variable>
,<false clause>
se ignora y se ejecuta la siguiente instrucción.<expression>
evalúa como falso,<true clause>
se ignora y<false clause>
se asigna el valor de<variable>
.Lo importante que hay que tener en cuenta con el operador ternario en este y otros lenguajes es que cualquier código que se encuentre
<expression>
debe producir un resultado booleano cuando se evalúe: verdadero o falso.En el caso de su ejemplo, reemplace "asignado a" en mi explicación con "agregado a", o similar para cualquier aritmética taquigráfica que esté utilizando, si corresponde.
fuente
+
tiene mayor precedencia que el operador condicional / ternario (de hecho, el operador condicional es casi siempre el último) evaluado en cualquier expresión).El
+=
hace lo que quiere, pero en la declaración ternaria a la derecha de él, verifica sih.className
es falso, que sería si no estuviera definido. Si es veraz (es decir, si el nombre de una clase ya está especificado), entonces el error se agrega con un espacio (es decir, agrega una nueva clase), de lo contrario, se agrega sin el espacio.El código podría reescribirse como sugiere, pero debe especificar que
h.className
se usará para la comparación de veracidad, en lugar de usar su valor real, en el operador ternario, así que asegúrese de no molestarse con la concatenación de valores. al mismo tiempo que realiza su operación ternaria:fuente
undefined
no es falso , solo se trata como si lo fueraEl lado derecho del
=
operador se evalúa de izquierda a derecha. Entonces,es equivalente a
Ser equivalente a
tienes que separar la declaración ternaria entre paréntesis
fuente
debe ser equivalente a:
fuente
Sé que esta es una pregunta muy antigua, pero no estoy 100% satisfecho con ninguna de las respuestas, ya que todas parecen incompletas. Así que aquí vamos de nuevo desde los primeros principios:
El objetivo general del usuario:
Resumiendo el código: "Deseo agregar un
error
nombre de clase a una cadena, opcionalmente con un espacio inicial si ya hay nombres de clase en la cadena".La solución más sencilla
Como señaló Kobi, hace 5 años, tener un espacio inicial en los nombres de las clases no causará ningún problema con ningún navegador conocido, por lo que la solución correcta más corta sería:
Eso debería haber sido la respuesta real al problema real .
Sea como fuere, las preguntas que se hicieron fueron ...
1) ¿Por qué funcionó esto?
El operador condicional / ternario funciona como una instrucción if, que asigna el resultado de sus rutas
true
ofalse
a una variable.Entonces ese código funcionó porque se evalúa simplemente como:
2) y ¿por qué se rompió esto?
La pregunta dice "eso da un [n] error en mi consola", lo que puede inducirlo a pensar que el código no funciona . De hecho, el siguiente código se ejecuta, sin error , pero simplemente devuelve 'error' si la cadena no estaba vacía y 'error' si la cadena estaba vacía y por lo tanto no cumplía con los requisitos .
Ese código siempre da como resultado una cadena que contiene solo
' error'
o'error'
porque evalúa este pseudo código:La razón de esto es que el operador de adición (
+
a la gente común) tiene mayor "precedencia" (6) que el operador condicional / ternario (15). Sé que los números aparecen al revésPrecedencia simplemente significa que cada tipo de operador en un idioma se evalúa en un orden predefinido particular (y no solo de izquierda a derecha).
Referencia: precedencia del operador de JavaScript
Cómo cambiar el orden de evaluación:
Ahora que sabemos por qué falla, necesita saber cómo hacer que funcione.
Algunas otras respuestas hablan de cambiar la precedencia , pero no puedes . La precedencia está integrada en el idioma. Eso es solo un conjunto fijo de reglas ... Sin embargo, puede cambiar el orden de evaluación ...
La herramienta de nuestra caja de herramientas que puede cambiar el orden de evaluación es el operador de agrupación (también conocido como corchetes). Para ello, se asegura de que las expresiones entre corchetes se evalúen antes de las operaciones fuera de los corchetes. Eso es todo lo que hacen, pero es suficiente.
Los corchetes funcionan simplemente porque ellos (operadores de agrupación) tienen mayor precedencia que todos los demás operadores ("ahora hay un nivel 0").
Simplemente agregando corchetes, cambia el orden de evaluación para garantizar que la prueba condicional se realice primero, antes de la concatenación de cadenas simple:
Ahora dejaré esta respuesta para que no se vea entre las demás :)
fuente
Me gustaría elegir una explicación de Wayne:
Consideremos ambos casos:
explanation
mientras que case2:
h.className + h.className
=> considerado como expresión para el operador ternario, ya que el operador ternario tiene mayor prioridad. entonces, siempre el resultado de la expresión ternaria simplemente se asignaNecesita definir la precedencia usando corchetesDebe definir el orden de evaluación que se considerará con la ayuda de paréntesis para que el caso 2 funcione como el caso 1
fuente