<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    BaSaRa 目前關心的是UI技術

    [引用] 對閉包的理解

    今天在群里面瞎談,就談到“閉包”上來了,何種語言支持閉包?自己g下吧,其中JavaScript是支持閉包概念的一種語言/腳本(?)。以下是我對他的見解(以javascript舉例)。

    先了解下在一個對象內如何聲明變量,一下以Test對象為例:
    Public變量:
    function Test()
    {
        
    this.x = 1;
    }
    或者
    Test.prototype.x = 1;
    公共變量簡而言之,外界對象可以對公共變量訪問,并且公共變量可以在對象的構造函數中聲明外,還可以在對象的prototype成員中聲明。換句話說,你可以在任何時候添加公共變量(利用prototype)。prototype是一個特別的成員變量,js就是利用這個成員變量的特性來實現繼承的。當一個成員被檢索且沒有在對象中發現的時候,那么它就會從對象構造器的prototype成員中獲取他。如果要從外界調用這個對象的方法,或者是通過這個方法操作這個對象里面的所有成員,你可以通過prototype加入:
    Test.prototype.Plus = function () {}

    Private變量:
    function Test()
    {
        
    var self = this;
        
        
    var x = 1;
        
        
    function Plus1() {}
        
        
    var pPlus = function Plus2() {}
    }
    私有的變量只能由成員的私有方法或者是特權方法(Privileged,下面講到)訪問,需要注意的是,上面的Plus1()這個方法和pPlus()這個方法是一樣的,只是聲明的方式不通而已,他們都是私有方法,他和特權變量的聲明方法很相似,只是少了個this多了個var,但是他們是不同的,應該特別注意。另外一點是,私有變量是在無法被外界訪問的同時,他也不能由對象的公共方法訪問。私有方法只是在構造函數內的內部方法。私有變量只能在構造函數中聲明。

    Privileged變量:
    function Test()
    {
        
    this.pPlus = function () {}
    }
    什么叫Privileged(特權)變量呢?特權方法可以訪問私有方法和私有變量,同時他對外界是可見的。你可以重新聲明這個私有方法或者是刪除他(重新對這個特權方法賦值,null值表示刪除),但是不能改變他。特權變量也只能在構造函數中聲明。

    好了,對象聲明介紹到這里,這些聲明模式都是由js的closure(閉包)特性所支持的,下面介紹閉包。

    在一個閉包內,你可以暫且(?)理解成在構造函數內,內部函數總是可以訪問函數外部的變量和參數的。就算在內部函數return后,閉包內的所有變量都會被保存起來,就好像一個上下文一樣。下面我以一個例子說明這個問題,例子來源在群內,由YOK提供(例子已經被修改,只是用來簡單說明問題)。

    說明:按test按鈕輸出相加的值,期望值為3。
    <html>
        
    <body>
            
    <input type="button" id="test" value="test" />
            
    <script>
    function Test (x, y)
    {
        
    var x = x;
        
    var y = y;
    }
    Test.prototype.add 
    = function ()
    {
        alert(
    this.x + this.y);
    }

    var t = new Test(12);
    document.getElementById('test').onclick 
    = t.add;
            
    </script>
        
    </body>
    </html>

    運行例子,但是輸出"NaN"。這是什么問題呢,我最初調試的時候,以為是this的問題,我原本理解成在add方法中this是指向test按鈕(其實this指向window對象),而他不包含x和y的兩個變量,所以輸出錯誤。首先,這個理解是正確的,但是你要如何修改才能獲取正確的結果呢。我們已經知道,在Test構造函數中,我們聲明的x,y是兩個私有變量,你不可能在外部訪問到,所以必須另覓他路。我們利用特權變量來解決。
    <html>
        
    <body>
            
    <input type="button" id="test" value="test" NAME="test"/>
            
    <script>
    function Test (x, y)
    {
        
    var x = x;
        
    var y = y;
        
        
    this.add = function ()    // 特權變量,可以訪問私有變量,又對外公開
        {
            alert(x 
    + y);
        }
    }

    var t = new Test(12);
    document.getElementById('test').onclick 
    = t.add;
            
    </script>
        
    </body>
    </html>

    上面呈現的是閉包的其中一個特性,下面用來說他的另外一個特性。
    <html>
        
    <body>
            
    <input type="button" id="test" value="test" NAME="test"/>
            
    <script>
    function Test ()
    {
        
    var z = 1;
        
        
    this.add = function ()
        {
            alert(z
    ++);
        }
    }

    var t = new Test();
    document.getElementById('test').onclick 
    = t.add;
            
    </script>
        
    </body>
    </html>
    每次輸出,值都會增加1,說明閉包內上下文就算add方法return后都會被保存。

    最后說下怎么動態替換行為(這里是按鈕click的行為)。
    <html>
        
    <body>
            
    <input type="button" id="test" value="test" NAME="test"/>
            
    <script>
    function Test ()
    {
        
    var z = 1;
        
    var self = this;
        
    var pBtn = null;
        
        
    this.selfSubtract = function ()
        {
            z
    --;z--;
            alert(z);
            pBtn.onclick 
    = self.selfPlus;
        }
        
        
    this.selfPlus = function ()
        {
            z
    ++;
            alert(z);
            pBtn.onclick 
    = self.selfSubtract;
        }
        
        
    this.getFunction = function (btn)
        {
            pBtn 
    = btn;
            
    return self.selfSubtract;
        }
    }

    var t = new Test();
    var btn = document.getElementById('test');
    btn.onclick 
    = t.getFunction(btn);
            
    </script>
        
    </body>
    </html>
    以上是我對他的一點見解,closure是js的一個特性而已,我們可以利用這個特性使設計更靈活,其他語言,我google到的好像叫Lua,不知道他是什么,他也支持。由于對js了解不深,請高手斧正確,enjoy it~~~ :)

    posted on 2006-06-13 11:13 BaSaRa 閱讀(298) 評論(0)  編輯  收藏 所屬分類: Javascript

    My Links

    Blog Stats

    常用鏈接

    留言簿(1)

    隨筆分類

    隨筆檔案

    搜索

    最新評論

    閱讀排行榜

    評論排行榜

    主站蜘蛛池模板: 久久亚洲高清观看| 亚洲av乱码一区二区三区香蕉| 亚洲另类少妇17p| 国产亚洲AV手机在线观看| 成人精品综合免费视频| 日韩精品电影一区亚洲| 成年免费a级毛片| 中文字幕亚洲图片| 99精品视频免费| 久久综合图区亚洲综合图区| 中文字幕无码一区二区免费| 亚洲AV无码国产丝袜在线观看 | 亚洲无码视频在线| 亚洲国产亚洲片在线观看播放| 国产美女视频免费观看的网站| 国产AⅤ无码专区亚洲AV| 97在线视频免费公开视频| 亚洲国产AV无码专区亚洲AV| 黄网站免费在线观看| 亚洲美女在线国产| 成人精品视频99在线观看免费| 日韩黄色免费观看| 日本一区二区三区免费高清在线 | 91免费国产精品| 亚洲综合激情另类专区| 三年片在线观看免费西瓜视频| 亚洲黄色免费网站| 好男人视频在线观看免费看片 | 三年片在线观看免费大全 | 中文字幕亚洲综合小综合在线| 日本高清免费中文字幕不卡| aaa毛片视频免费观看| 亚洲大片免费观看| 亚洲精品在线免费观看| 久久精品亚洲中文字幕无码麻豆| 久久精品女人天堂AV免费观看| 美女黄色免费网站| 久久精品蜜芽亚洲国产AV| 啊v在线免费观看| 亚洲AV无码国产精品永久一区| 中文字幕中韩乱码亚洲大片|