zoukankan      html  css  js  c++  java
  • An Example for Javascript Function Scoping and Closure

    1. An Real World Example

    In the patron detail page of the CRM system I'm working with, there’re large amount of data. To shorten user’s waiting time, we want to only load basic information at page loaded then dynamically load the others in ajax.

    Now we’re going to call ajax in a “for” loop:

    var subpanelIDs = ['panel1', 'panel2', 'panel3'];
    function loadSubpanels() {
       for (var i = 0; i < subpanelIDs.length; i++) {
            var panelID = subpanelIDs[i];
            var successFunc = function (resultHtml) {
                    console.log(panelID);  //!!!It console 'panel3’ for 3 times
                    //$('#'+panelID).html(resultHtml);
            };
            $.ajax({
                url: url,
                dataType: "html",
                success: successFunc
            });
        }
    }
    loadSubpanels();
    In the success call back, we want to find element with an id “panelID” and fill the html to it. But unluckily the panelID is always “panel3”.

    2. Function Scoping in Javascript

    It’s about function scoping and closure.

    Javascript is a lexical scoping language, also called static scoping, that means if a variable name's scope is a certain function, then its scope is the program text of the function definition: within that text, the variable name exists, and is bound to the variable's value, but outside that text, the variable name does not exist.

    In our example, panelID’s scope is the text of whole function loadSubpanels. The 3 times of invoking “successFunc” are within a single invoking of “loadSubpanels”, so the current scope chain is shared by 3 “successFunc”. And result is that they all getting the same value of ‘panel3’.

    Here we’re not going to explain detail for scoping and closure, you can refer to the book “javascript.the.definitive.guide”

    3. Resolution

    To avoid the 3 invoking of “successFunc” sharing same scope chain, we need to seperate them into another function “loadOnePanel”.

    In this case each loadOnePanel will own a scope chain the the value of panelID will not change unexpectedly. The call back function now can fill 3 panels accrodingly.

    var subpanelIDs = ['panel1', 'panel2', 'panel3'];
    function loadSubpanels() {
       for (var i = 0; i < subpanelIDs.length; i++) {
            loadOnePanel(subpanelIDs[i]);
        }
    }
    function loadOnePanel(panelID){
        var successFunc = function (resultHtml) {
            console.log(panelID);
        };
        $.ajax({
            url: url,
            dataType: "html",
            success: successFunc
        });
    }
    loadSubpanels();
  • 相关阅读:
    几个很实用的BOM属性对象方法
    JavaScript hash
    WPF中ControlTemplate和DataTemplate的区别
    C#性能测试方法
    Lc.exe已退出,代码为-1
    C#遍历enum类型
    WPF画线问题,几千条以后就有明显的延迟了。
    WPF学习笔记(3):Path绘制命令zz
    WPF: 旋转Thumb后,DragDelta移动距离出错的解决
    在Revit中如何显示附件模块(Add Ins) 这个命令页?zz
  • 原文地址:https://www.cnblogs.com/hiteddy/p/An_Example_on_Closure_and_Javascript_function_scope.html
Copyright © 2011-2022 走看看