Maison > interface Web > js tutoriel > Une brève analyse des exemples d'utilisation de la fermeture javascript (Closure)_compétences javascript

Une brève analyse des exemples d'utilisation de la fermeture javascript (Closure)_compétences javascript

WBOY
Libérer: 2016-05-16 15:29:01
original
1123 Les gens l'ont consulté

L'exemple de cet article décrit l'utilisation de la fermeture javascript (Closure). Partagez-le avec tout le monde pour votre référence, les détails sont les suivants :

closure se traduit par "closure", et j'ai l'impression que cette chose est présentée de manière trop académique. Discutons-en brièvement en faisant référence à des livres et des ressources en ligne (veuillez faire attention à toute compréhension inappropriée).

1. Qu'est-ce que la fermeture

Réponse officielle : La soi-disant « fermeture » ​​fait référence à une expression (généralement une fonction) qui a de nombreuses variables et un environnement lié à ces variables, donc ces variables font également partie de l'expression.

Après avoir lu la définition ci-dessus, si vous n'êtes pas un expert, je crois fermement que vous demanderez avec colère comme moi : est-ce un langage humain tmd ?
Pour comprendre les fermetures, le code est le plus convaincant Voici le code :

function funcTest()
{
 var tmpNum=100; //私有变量
 //在函数funcTest内定义另外的函数作为funcTest的方法函数
 function innerFuncTest(
 {
    alert(tmpNum); //引用外层函数funcTest的临时变量tmpNum
 }
 return innerFuncTest; //返回内部函数
}
//调用函数
var myFuncTest=funcTest(); 
myFuncTest();//弹出100

Copier après la connexion

Dans le code ci-dessus, les commentaires ont été écrits clairement. Maintenant, nous pouvons comprendre la « fermeture » comme ceci : définir une autre fonction dans le corps de la fonction comme fonction de méthode de l'objet cible (dans l'exemple, définir une autre fonction innerFuncTest comme fonction de méthode de funcTest dans la fonction funcTest), et la fonction de méthode de cet objet est le contraire. Venons-en à référencer les variables temporaires dans le corps de la fonction externe (la fermeture est un mécanisme permettant de maintenir indirectement les valeurs des variables. Dans l'exemple, la fonction interne innerFuncTest fait référence à la variable temporaire tmpNum de la fonction externe funcTest. Elle Il faut noter ici que les variables temporaires peuvent être incluses dans la fonction externe (toutes les variables locales déclarées, les paramètres et autres fonctions internes déclarées). Lorsqu'une de ces fonctions internes est appelée en dehors de la fonction externe qui les contient, une fermeture est formée (dans l'exemple, lors de l'appel de la fonction, myFuncTest appelle en fait la fonction innerFuncTest, ce qui signifie qu'une fonction interne de funcTest, innerFuncTest est appelée en dehors funcTest, une fermeture est créée).

2. Deux exemples d'utilisation de fermetures

Voici deux exemples. L'un est dû au fait que les fermetures causent des problèmes, et l'autre utilise des fermetures pour lier intelligemment les paramètres via la portée d'une fonction.

Les fragments de balisage HTML liés à ces deux exemples sont les suivants :

<a href="#" id="closureTest0">利用闭包的例子(1秒后会看到提示)</a><br />
<a href="#" id="closureTest1">由于闭包导致问题的例子1</a><br />
<a href="#" id="closureTest2">由于闭包导致问题的例子2</a><br />
<a href="#" id="closureTest3">由于闭包导致问题的例子3</a><br />

Copier après la connexion

(1) Problèmes causés par les fermetures

Il y a 4 éléments dans le fragment de balise HTML ci-dessus. Nous devons maintenant attribuer des gestionnaires d'événements aux trois derniers afin qu'ils signalent leur ordre dans la page lorsque l'utilisateur clique. Lors d'un lien vers le 2ème lien, il indique "Vous avez cliqué sur le 1er lien". Pour ce faire, si vous écrivez la fonction suivante qui ajoute des gestionnaires d'événements pour les trois derniers liens :

function badClosureExample(){
  for (var i = 1; i <4; i++) {
    var element = document.getElementById('closureTest' + i);
    element .onclick = function(){
      alert('您单击的是第' + i + '个链接');
    }
  }
}

Copier après la connexion

Ensuite, appelez cette fonction après le chargement de la page (sinon une erreur pourrait être signalée) :

window.onload = function(){
  badClosureExample();
}

Copier après la connexion

Regardez les résultats en cours d'exécution. Si vous cliquez sur les trois derniers liens, quelles informations verrez-vous dans la boîte d'avertissement ? ——C'est tout "Vous avez cliqué sur le 4ème lien". Cela vous surprend ? Pourquoi?

Analyse : parce que le gestionnaire d'événements attribué à element.onclick dans la fonction badClosureExample(), c'est-à-dire que la fonction anonyme onclick n'est appelée qu'une fois la fonction badClosureExample() terminée (lorsque l'utilisateur clique sur le lien). Lors de l'appel, la variable i doit être évaluée. L'analyseur recherchera d'abord dans le gestionnaire d'événements, mais i n'est pas défini. Ensuite, recherchez dans la fonction badClosureExample(). Elle est définie à ce moment-là, mais la valeur de i est 4 (la boucle for cessera de s'exécuter uniquement si i est supérieur à 4). Par conséquent, cette valeur est obtenue - exactement ce que ferait la fermeture (fonction anonyme) si elle utilisait une variable dans le cadre de sa fonction externe (badClosureExample). De plus, cela est également dû au fait que la fonction anonyme elle-même ne peut pas transmettre de paramètres (et ne peut donc pas conserver sa propre portée).

Alors, comment résoudre le problème dans cet exemple ? En fait, il existe de nombreuses méthodes (autant l'écrire vous-même et voir). Je pense que le code est relativement simple et direct :

function popNum(oNum){
  return function(){
          alert('您单击的是第'+oNum+'个链接');
  }
}
function badClosureExample(){
  for (var i = 1; i <4; i++) {
    var element = document.getElementById('closureTest' + i);
    element .onclick =new popNum(i);
    }
}

Copier après la connexion

(2), utilisation intelligente des fermetures pour lier les paramètres

Toujours avec le fragment HTML ci-dessus, nous souhaitons retarder l'apparition d'une boîte d'avertissement lorsque l'utilisateur clique sur le premier lien. Comment y parvenir ? La réponse est d'utiliser la fonction setTimeout(), qui appelle une fonction après un nombre spécifié de millisecondes, comme :

Copier le code Le code est le suivant :
setTimeout(someFunc,1000);

Mais le problème est que les paramètres ne peuvent pas être transmis à la fonction someFunc. Ce problème peut être facilement résolu en utilisant des fermetures :

function goodClosureExample(oMsg){
  return function(){
    alert(oMsg);
  };
}

Copier après la connexion

La fonction goodClosureExample est utilisée pour renvoyer une fonction anonyme (fermeture). Et nous pouvons faire en sorte que la fonction anonyme renvoyée lie le paramètre en lui passant un paramètre, tel que :

Copier le code Le code est le suivant :
var good = goodClosureExample('Ce paramètre est lié par une fermeture') ;

而此时,就可以将绑定了参数的good函数传递给setTimeout()实现延时警告了:
复制代码 代码如下:
setTimeout(good,1000) //此时good中已经绑定了参数

最后,测试通过的完整代码:

window.onload = function(){
  var element = document.getElementById('closureTest0');
  if (element) {
    var good = goodClosureExample('这个参数是由闭包绑定的');
    element.onclick = function(){
      setTimeout(good, 1000); //延迟1秒弹出提示
    }
  }
}

Copier après la connexion

3、javascript的垃圾回收原理

(1)、在javascript中,如果一个对象不再被引用,那么这个对象就会被GC回收;

(2)、如果两个对象互相引用,而不再被第3者所引用,那么这两个互相引用的对象也会被回收。

在js中使用闭包,往往会给javascript的垃圾回收器制造难题。尤其是遇到对象间复杂的循环引用时,垃圾回收的判断逻辑非常复杂,搞不好就有内存泄漏的危险,所以,慎用闭包。ms貌似已经不建议使用闭包了。

希望本文所述对大家JavaScript程序设计有所帮助。

É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