Maison > interface Web > js tutoriel > le corps du texte

Analyse d'un entretien de clôture frontal JS question_javascript skills

WBOY
Libérer: 2016-05-16 15:23:28
original
1707 Les gens l'ont consulté

Question

Code A

function fun(n,o){
  console.log(o);
  return {
    fun:function(m){//[2]
      return fun(m,n);//[1]
    }
  }
}

var a=fun(0);
a.fun(1);
a.fun(2);
a.fun(3);
var b=fun(0).fun(1).fun(2).fun(3);
var c=fun(0).fun(1);
c.fun(2);
c.fun(3);
Copier après la connexion

Trouver la sortie du programme

Ceci est une question de test de clôture

Convertir en code équivalent

L'attribut fun de l'objet renvoyé par return correspond à un objet fonction nouvellement créé. Cet objet fonction formera une portée de fermeture, lui permettant d'accéder à la variable n de la fonction externe et à la fonction externe fun. combiner la fonction fun avec L'attribut fun est confus, on modifie le code ci-dessus comme suit :
Code B

function _fun_(n,o){
  console.log(o);
  return {
    fun:function(m){
      return _fun_(m,n);
    }
  }
}

var a=_fun_(0);//undefined
a.fun(1);//0
a.fun(2);//0
a.fun(3);//0

var b=_fun_(0).fun(1).fun(2).fun(3);
//undefined,0,1,2

var c=fun(0).fun(1);//undefined,0,
c.fun(2);//1
c.fun(3); //1

Copier après la connexion

Ensuite, certains étudiants ont demandé, pourquoi cela peut-il être modifié comme ça ? Comment pouvez-vous être sûr que le plaisir en [1] n'est pas le plaisir en [2] où se trouve le code ? Vous devez savoir que l'attribut fun ici ? pointe vers un objet fonction ~
Nous parlons ici de la portée lexicale de JS. La portée de la variable JS existe dans le corps de la fonction, c'est-à-dire le corps de la fonction, et la portée de la variable est déterminée lorsque la définition de la fonction est déclarée, et non lorsque la fonction est exécutée.
Le code suivant

var name="global";
function foo(){
  console.log(name);
}

function fooOuter1(){
  var name="local";
  foo();
}
fooOuter1();//输出global 而不是local,并且和闭包没有任何关系

function fooOuter2(){
  var name="local";
  function foo(){
    console.log(name);
  }
  foo();
}
fooOuter2();//输出local 而不是global,在函数声明是name变量作用域就在其外层函数中,嗯嗯就是闭包~<br />
Copier après la connexion

D'accord, revenons au sujet. Dans l'étape de définition de la déclaration de fonction, la fonction anonyme en [2] est définie et déclarée qu'un objet fonction nommé fun doit être référencé en [1]. recherchez-le d'abord dans le corps de la fonction actuelle. Si vous trouvez qu'il n'est pas trouvé, accédez à sa fonction externe - la fonction d'emballage de cette fonction anonyme pour rechercher, et vous constatez qu'il n'est pas trouvé. Accédez à la fonction externe et. trouvez qu'il n'y a pas de wrapper de fonction à l'extérieur, puis allez dans l'environnement global pour le trouver, hein. Je l'ai enfin trouvé... Spécifiez simplement la fonction fun comme objet de fonction fun dans l'environnement global et ajoutez-la à la fermeture de l'anonyme. fonction. À ce stade, nous savons pourquoi le code B est équivalent au code A~~~

Créer une portée de fermeture

Après l'analyse lexicale, JS détermine une fermeture, qui est la fermeture de la fonction anonyme correspondant à l'attribut fun de l'objet renvoyé - la fonction variable interne n qui accède à _func_ dans l'environnement global et sa fonction externe <🎜 ; > Chaque fois que _func_ est exécuté, les informations de portée des variables dans la fermeture seront transmises à l'environnement d'exécution de la fonction pour être utilisées lors de l'obtention de la valeur de la variable lorsque la fonction est exécutée

Sortie d'exécution

var a=_fun_(0);//undefined
a.fun(1);//0
a.fun(2);//0
a.fun(3);//0
Copier après la connexion
La fonction _fun_ est exécutée, car le deuxième paramètre n'est pas défini, la sortie est indéfinie. Renvoyez ensuite un objet avec l'attribut fun pointant vers un objet fonction - avec une fermeture, capable d'accéder à _fun_ et à la variable n_

a.fun(1) exécute la méthode fun de l'objet renvoyé, transmet la valeur de m 1 et l'appel renvoie _fun_(1,0)
La sortie est donc 0, a.fun(2), a.fun(3) et a.fun(1)

var b=_fun_(0).fun(1).fun(2).fun(3); Code équivalent :

var b=_fun_(0); var b1=b.fun(1);
var b2=b1.fun(2);//[3]
var b3=b2.fun(3);//[4]

Les deux premières phrases sont identiques à la sortie ci-dessus undefined,0 Lorsque [3] est appelé, il y a une fermeture dans l'objet b1, qui fait référence à la fonction _fun_ et à la variable de fonction externe n=1. , donc L'appel de fonction effectué par la fonction anonyme est _fun_(2,1), le résultat de sortie est 1 et un nouvel objet est renvoyé.
Lorsque [4] est exécuté, l'objet b2 a également une fermeture, qui fait référence à la fonction _fun_ et à la variable de fonction externe n=2. Lorsque _fun_(3,2) est exécuté, le résultat de sortie est 2
.

var c=fun(0).fun(1);//undefined,0,
c.fun(2);//1
c.fun(3); //1
Copier après la connexion
Si vous pouvez comprendre l'explication précédente de l'exécution de code et comprendre le résultat de l'exécution de code ci-dessus, il n'y aura aucun problème.

Étiquettes associées:
source:php.cn
Déclaration de ce site Web
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn
Tutoriels populaires
Plus>
Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal