Usamos declaraciones de retorno opcionalmente en funciones de JavaScript. Es una palabra clave. Pero, ¿cuál es el tipo real de return
sí mismo? En realidad me confundí al ver el ejemplo:
function add(a, b) {
return (
console.log(a + b),
console.log(arguments)
);
}
add(2, 2);
Salida:
4
[2, 2]
Entonces, podemos pasar expresiones separadas por comas a la return
declaración. ¿Es esta una función?
Y comenzando con esto, ¿podemos suponer que cada palabra clave en JavaScript es en última instancia una función?
He escrito un pequeño blog como parte esencial de esta discusión. Es posible que desee comprobarlo aquí .
javascript
return
keyword
Arnab Das
fuente
fuente
var a = (2 + 2)
.var a = (1, 2)
: esto resultará ena
tener el valor2
debido a cómo opera el operador de coma (sí, la coma es un operador matemático como+
o|
etc., específicamente, en el cálculo lambada, el operador de coma implementa el combinador K)Respuestas:
No tiene un tipo, no es un valor.
Intentarlo
typeof return;
te daráUnexpected token return
.No, mientras que los paréntesis se pueden usar para llamar a una función, aquí son un operador de agrupación que contiene un par de expresiones separadas por un operador de coma .
Una demostración más útil sería:
Qué salidas
0
porque el resultado dea + b
se ignora (está en el LHS del operador de coma) ya - b
se devuelve.fuente
return
no llega a verlos, que es lo que estabas preguntando.a + b
simplemente no tiene ningún efecto visible porque no tiene efectos secundarios y el valor se descarta (bueno, dado que no tiene ningún efecto práctico, es posible que un compilador optimizador lo elimine, pero eso no hace ninguna diferencia práctica).if
) es la evaluación de cortocircuito. El operador de coma no cortocircuita, por lo que evaluará ambos lados. Luego devolverá el último. Ese es explícitamente el propósito del operador de coma, agrupar expresiones en una sola declaración (generalmente se ignora el valor resultante de toda la declaración), que se usa con mayor frecuencia para la inicialización de variables:var i = 2, j = 3, k = 4;
Estoy un poco sorprendido de que nadie aquí haya hecho referencia directa a la especificación :
Entonces, debido a la especificación, su ejemplo dice:
return ( GetValue(exprRef) )
dónde
exprRef = console.log(a + b), console.log(arguments)
Que de acuerdo con la especificación del operador de coma ...
... significa que cada expresión se evaluará hasta el último elemento de la lista de comas, que se convierte en la expresión de asignación. Entonces tu código
return (console.log(a + b) , console.log(arguments))
va a1.) imprime el resultado de
a + b
2.) No queda nada por ejecutar, así que ejecute la siguiente expresión que
3.) imprime
arguments
, y porqueconsole.log()
no especifica una declaración de devolución4.) Evalúa como indefinido
5.) Que luego se devuelve a la persona que llama.
Entonces, la respuesta correcta es,
return
no tiene un tipo, solo devuelve el resultado de alguna expresión.Para la siguiente pregunta:
No. La coma en JavaScript es un operador, definido para permitirle combinar múltiples expresiones en una sola línea, y está definida por la especificación para devolver la expresión evaluada de lo que sea el último en su lista.
¿Aún no me crees?
Juega con ese código aquí y juega con el último valor de la lista. Siempre devolverá el último valor de la lista, en su caso, resulta ser
undefined.
Para su pregunta final,
De nuevo, no. Las funciones tienen una definición muy específica en el lenguaje. No lo volveré a imprimir aquí porque esta respuesta ya se está volviendo extremadamente larga.
fuente
Probando lo que sucede cuando devuelve valores entre paréntesis:
Da la respuesta
2
, por lo que parece que una lista de valores separados por comas se evalúa como el último elemento de la lista.Realmente, los paréntesis son irrelevantes aquí, están agrupando operaciones en lugar de significar una llamada a función. Sin embargo, lo que posiblemente sea sorprendente es que la coma es legal aquí. Encontré una publicación de blog interesante sobre cómo se maneja la coma aquí:
https://javascriptweblog.wordpress.com/2011/04/04/the-javascript-comma-operator/
fuente
return ([1, 2])
debería imprimir ambos valores?console.log((1, 2))
return
no es una función. Es la continuación de la función en la que ocurre.Piense en el enunciado
alert (2 * foo(bar));
dondefoo
está el nombre de una función. Cuando lo evalúa, ve que tiene que dejar de lado el resto de la declaración por un momento para concentrarse en evaluarfoo(bar)
. Podrías visualizar la parte que apartaste como algo asíalert (2 * _)
, con un espacio en blanco para completar. Cuando sabes cuál es el valor defoo(bar)
, retíralo.Lo que dejó de lado fue la continuación de la llamada
foo(bar)
.Llamar le
return
da valor a esa continuación.Cuando evalúas una función en el interior
foo
, el resto defoo
espera a que esa función se reduzca a un valor y luego lafoo
reanuda. Todavía tienes un objetivo que evaluarfoo(bar)
, simplemente está en pausa.Cuando evalúas el
return
interiorfoo
, ninguna parte defoo
espera por un valor.return
no se reduce a un valor en el lugar interiorfoo
donde lo usó. En cambio, hace que toda la llamada sefoo(bar)
reduzca a un valor, y el objetivo "evaluarfoo(bar)
" se considera completo y deslumbrado.La gente no suele informarle sobre las continuaciones cuando es nuevo en la programación. Ellos piensan que es un tema avanzado, simplemente porque no son cosas muy avanzadas que las personas eventualmente hacen con continuaciones. Pero la verdad es que los está usando todo el tiempo, cada vez que llama a una función.
fuente
alert(2 * _)
para su uso posterior en Javascript (hay una notación diferente para hacer ese tipo de cosas).return
desde adentrofoo
no es un valor; no podía empaquetarlo en una estructura de datos, asignarlo a una variable, esperar un tiempo y luego alimentarlo con algo más tarde, y especialmente no podía alimentarlo más de una vez. Pero, como dije, temas avanzados.my_if
función que se comporte como una función incorporadaif()then{}else{}
, y no hacerlo incluso si te permites usar la función incorporada dentro de ella, no es terriblemente avanzada y enormemente instructiva, especialmente si vas a terminar en código que transmite devoluciones de llamada.el
return
aquí es una pista falsa. Quizás sea interesante la siguiente variación:que sale como la última línea
ya que la función en realidad no devuelve nada. (Devolvería el valor de retorno del segundo
console.log
, si tuviera uno).Tal como está, el código es exactamente idéntico a
fuente
Una forma interesante de entender la declaración de retorno es a través del operador void . Eche un vistazo a este código.
Dado que la
return
declaración toma un argumento que es[[expression]]
y lo devuelve a la persona que llama en la pila, es decirarguments.callee.caller
, se ejecutarávoid(expression)
y luego devolverá,undefined
esa es la evaluación del operador void.fuente