función
Formato de función
función getPrototynames (o,/*opcional*/ a) {a = a || []; para (var p en o) {a.push (p);} return a;}Llamador
FURC.Caller Devuelve la persona que llama
función callFunc () {if (callfunc.caller) {alert (callFunc.caller.ToString ());} else {alert ("sin función de la función");}} function handlecaller () {callFunc ();} handlecaller (); // returnCallFunc (); // no función de función, return null, no se ejecute "no se ejecute" no se ejecute "no," no se ejecute "Calling".callejón
Llamada recursiva del método anónimo
alert ((function (x) {if (x <=) return; return x * arguments.callee (x -);} ())); //alcance
Todos están familiarizados con el alcance. Hoy hablaré sobre el problema de cierre y comprenderé el problema de cierre a fondo.
<script> var global = "alcance global"; // Este es el alcance de la función de alcance global () {var alcance = "alcance local"; // Este es el alcance de retorno del alcance local; // El alcance devuelto es una variable local} </script>1.: También se puede acceder a las variables globales definidas dentro de la función . Cuando la variable local definida y el nombre de la variable global son los mismos, la variable local ocultará la variable global y no destruirá el valor de la variable global.
var Scope = "Global Scope"; function f () {var Scope = "Local Scope"; return Scope;} alert (f ()); // scopealert local (alcance); // alcance global;Lo anterior es realmente fácil de entender, ¿verdad?
2. Las variables globales se pueden declarar sin VAR , pero las variables locales deben declararse con VAR. Si las variables locales no usan la declaración de VAR, el compilador se predeterminará a esto como una variable global.
<span style = "Line-Hight:.; Font-Family: Verdana, Arial, Helvetica, Sans-Serif; Font-Size: Px; Background-Color: Rgb (,,);"> </span> Scope = "Global Scope"; function f () {Scope = "Local Scope"; SCOPE de retorno;Sin embargo, las variables globales no usan declaraciones de VAR, y solo están disponibles para el modo no riguroso. Si se usa el modo estricto, se informará un error.
<script> "Use Strict"; Scope = "Global Scope"; function f () {Scope = "Local Scope"; return Scope;} alert (f ()); // local scopealert (alcance); // alcance local </script>Por lo tanto, se recomienda que no omita VAR al declarar variables, ya que puede evitar problemas innecesarios.
3. Está bien declararse de antemano . ¿Qué es lo que está con anticipación?
<script> "use estricto"; alcance; console.log (scope); var scope = "global scope"; console.log (alcance); </script>
Esto puede verse como el primero en imprimir indefinido. Sí, aún no se le ha asignado un valor. La siguiente asignación puede determinar el alcance global.
Esto no está mal, pero ¿por qué está sucediendo esto? ¿No se debe definir una variable antes de que se pueda usar?
Aquí te contaré sobre la cadena de alcance. JavaScript es un lenguaje léxico de alcance.
1. Una cadena de alcance es un objeto o una lista vinculada. Este conjunto de código define las variables "en el alcance" de este código. Cuando JavaScript necesita encontrar el alcance variable, se desarrollará y buscará desde el primer objeto de la cadena. Si el primer objeto es alcance, el valor de este objeto se devolverá directamente. Si no existe, continuará buscando el segundo objeto hasta que se encuentre. Si la variable no se encuentra en la cadena de alcance, se lanzará un error.
Podemos expresar esta cadena de funciones de la siguiente manera: encontrar el alcance-> ventana (objeto global) y luego se define el alcance. Sin embargo, la operación de asignación no se realizó, y la operación de asignación se realizó más tarde, por lo que el valor no está definido en este momento.
4. Esto es más confuso. ¿Cuál es el valor impreso?
<Script> "Use Strict"; var Scope = "Global Scope"; function f () {console.log (scope); var Scope = "Local Scope"; Console.log (Scope);} f (); </script>Vea este código: si es descuidado, puede escribir la respuesta incorrecta:
1. Alcance de GoBal
2. Alcance local
Análisis: Declarar variables globales. Cuando está en el cuerpo de la función, el primero representa la variable global, por lo que se imprime Global y el segundo define las variables locales, cubriendo el alcance global, por lo que se imprime el alcance local.
Tal análisis es completamente correcto en C# Java. Pero el análisis aquí es realmente incorrecto.
Esto muestra que antes de este problema, veamos una pregunta primero.
Esta oración es muy importante: las variables globales siempre se definen en el programa. Las variables locales siempre se definen dentro del cuerpo de la función que la declara y las funciones que anuda.
Si está trabajando en un idioma de alto nivel, está expuesto a JavaScript un poco inadecuado para su definición de alcance. Soy lo mismo. Echemos un vistazo a un ejemplo:
<script> var g = "global scope"; function f () {for (var i =; i <; i ++) {for (var j =; j <; j ++) {;} console.log (j);} console.log (i);} console.log (g); f (); </script>¿Cuál es el resultado de la impresión?
Usted ve que {} representa un bloque de declaración, y el bloque de instrucciones está en el alcance del mismo bloque, por lo que puede suponer que los valores J e I se han lanzado en la memoria, por lo que el resultado debe ser indefinido.
El verdadero resultado puede decepcionarte.
¿Por qué sucedió esto? Mi expresión comenzó como tú.
Echa un vistazo a la oración que te pedí que recordara ahora. . . Las variables globales siempre se definen en el programa. Las variables locales siempre se definen dentro del cuerpo de la función que la declara y las funciones que anuda.
Para ser precisos, los parámetros de la función también pertenecen a la categoría de variables locales. ¡Esta oración también es muy importante! ! !
Esa oración significa aproximadamente que mientras una variable definida dentro de una función sea válida dentro de toda la función. Entonces el resultado no es difícil de entender. Mirando hacia atrás en nuestra pregunta, ¿entiendes?
La cadena de acción también tiene las siguientes definiciones:
1. La cadena de acción está compuesta por un objeto global.
2. En el cuerpo de la función que no contiene anidación, hay dos objetos en la cadena de acción. El primer objeto define los parámetros de la función y las variables locales, y el segundo es el objeto global.
3. En un cuerpo de función anidada, hay al menos tres objetos en la cadena de acción.
Cuando se define una función, se guardará una cadena de alcance.
Cuando se llama a esta función, crea un nuevo objeto para almacenar sus variables locales y agrega este objeto a la cadena de acción guardada. Al mismo tiempo, cree una nueva cadena de funciones más largas que representan llamadas de funciones.
Para las funciones anidadas, cuando se llama la función externa, la función interna se redefinirá nuevamente. Porque cada vez que se llama a una función externa, la cadena de acción es diferente. Las funciones internas tienen diferencias sutiles cada vez que se definen. Cada vez que se llama a la función externa, el código de la función interna es el mismo, y el alcance del código asociado también es diferente.
Cierre
Después de hacerlo durante tanto tiempo, finalmente pude hablar sobre eso, pero analicemos el alcance antes.
<script> var nameG = "global" var g = function f () {console.log (name); function demos () {console.log ("deloM =" + name);} var name = ""; function demo () {var name = ""; console.log ("damo =" + name);} function dMo () {console.log ("demo =" nameG);} demo (); demo (); demo ();}; g (); </script>Analizamos de acuerdo con la cadena de acción:
Llame a Demo0, demo0 () -> Buscar nombre, no encontrado -> f (), return
Llame a Demo1, demo1 ()-> Buscar nombre, buscar, regresar
Llame a Demo2, demo2 () -> Buscar nameG, no encontrado -> f () para encontrar nameG, no encontrado -> ventana para encontrar nameG, return.
Mira este ejemplo:
<script> function f () {var count =; return {contador: function () {return count ++;}, reset: function () {return count =;}}} var d = f (); var c = f (); console.log ("d la primera llamada:"+ d.Counter ()); // console.log ("Call:"+ c.Counter (); Llame: "+ C.counter ()); // </script>Como puede ver en este ejemplo, hice una operación de conteo y cero.
Se crean dos instancias de objetos de F, cada una con su propia cadena de alcance, por lo que sus valores no se afectan entre sí. Cuando C se llama por segunda vez, el valor de conteo se guarda porque el objeto C no se destruye. Solo después de comprender este ejemplo, el siguiente ejemplo será más fácil de entender.
Todos deberían ser muy claros sobre este proceso. Así que ahora veamos el problema de cierre. Configuré cuatro botones y hago clic en cada botón para devolver el nombre de la respuesta.
<body> <script> function btninit () {for (var i =; i <; i ++) {var btn = document.getElementById ("btn" + i); btn.adDeventListener ("click", function () {alerta ("btn" + i);});} winder.onload = btninit; </</script script id = "btn"> btn </boton> <botón id = "btn"> btn </boton> <button id = "btn"> btn </boton> <botón id = "btn"> btn </boton> </div> </body>Haga clic para ejecutar, pero el resultado es todo BTN5;
Nos sentamos con el análisis justo ahora. Primero, necesitamos llamar a la función anónima -> encontrar i, no encontrar -> btninit (), y encontré i en el bucle for. aparecer. Sabemos que solo se lanza la llamada de función, y el i in for iN siempre es visible, por lo que se conserva el último valor. Entonces, cómo resolverlo.
Para resolver el problema de que el valor I no siempre es visible en la función, necesitamos usar el anidado de la función y pasar el valor I.
función btninit () {for (var i =; i <; i ++) {(function (data_i) {var btn = document.getElementById ("btn" + data_i); btn.adDeventListener ("click", function () {alerta ("btn" + data_i);});} (i);}}}}Mirando el código modificado, primero ejecute el primero y cree un objeto. Primero ejecutamos la función anónima -> data_i, pero no encontramos -> función (data_i), y luego ejecutamos nuevamente para crear un objeto. Las reglas de cierre dicen que no se afectan entre sí. Entonces se puede obtener el resultado correcto.
Lo anterior es la función JavaScript Must-Know Know (9) que el Editor le presenta. Hablando del conocimiento relevante sobre temas de cierre, espero que sea útil para usted. Si tiene alguna pregunta, déjame un mensaje y el editor le responderá a tiempo. ¡Muchas gracias por su apoyo al sitio web de Wulin.com!