<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                合規國際互聯網加速 OSASE為企業客戶提供高速穩定SD-WAN國際加速解決方案。 廣告
                ## apply和call講解 為什么這兩個放在一起,使用過這兩個方法的都知道,他們在使用上,傳參方式不一樣,其他都一樣的;但是bind就要復雜些了。 ### 通俗話**原理** * 就是把A對象作用域(this)傳遞到B(函數)對象作用域中執行,B函數作用域中執行取決于在哪個執行環境(this)中。 * 埋個伏筆,先來看一下下面繼承,來對應一下上面這個描述,FB中this即是objA(注意:當FB原來this即是window對象),說明FB在經過objA.FB = FB時,FB環境已經改變。這個等閱讀完回過頭看,就會發現和call實現原理好像挺相似的。 ``` js function FB(age){ console.log('FB:this=',this) // {name: 'vvmily', FB: ?} this.age = age console.log(this.name,this.age) // vvmily 18 } var objA = { name: 'vvmily' } objA.FB = FB // objA.prototype.FB = FB objA.FB(18) ``` * 下面通過call方式,在表面可以看出objA.FB = FB與FB.call(this)作用一樣,把FB的執行作用域環境改變為FA的作用域(this)環境。 ``` js function FB(age){ this.age = age console.log(this.name, this.age) // vvmily 19 } function FA(){ this.name = 'vvmily' FB.call(this,19) } const a = new FA() ``` ### 總結 有了總結,知道call做了什么事情,才更好的實現,不是嗎。 1. 將當前執行作用域賦予另一個函數作用域 FB(this) => FA(this) 2. 另一個函數作用域執行結果返回(掛在)當前作用域 ### 手寫實現 ``` js function MyCall(context, ...args){ context = context || window // MyCall所在執行作用域的this,并非MyCall自己的this args = args || [] context.B_Fn = this // 保存當前MyCall執行作用域 const result = context.B_Fn(...args) // 執行當前作用域,并拿到結果,并且結果直接掛在執行的作用域中,而非MyCall作用域哦 delete context.B_Fn // 防止污染 return result } ``` 檢驗一下是否正確,當然是成功了 ``` js Function.prototype.MyCall = MyCall function FB(age){ this.age = age console.log(this.name, this.age) // vvmily 19 } function FA(){ this.name = 'vvmily' FB.MyCall(this,19) } const a = new FA() ``` ### apply手動實現 請仔細對比,基本args的區別,就是參數,這里FB.MyCall(this,[19])第二個參數為數組即可 ``` js function MyApply(context, args){ context = context || window // MyCall所在執行作用域的this,并非MyCall自己的this args = args || [] context.B_Fn = this // 保存當前MyCall執行作用域 const result = context.B_Fn(...args) // 執行當前作用域,并拿到結果,并且結果直接掛在執行的作用域中,而非MyCall作用域哦 delete context.B_Fn // 防止污染 return result } ``` ## bind講解 通俗講:將某個(對象,如objB)作用域作為(將要返回的)新函數體作為執行環境。 先來看看下面的代碼,感受一下上面這句話。 ``` js const objB = { name: 'vvmily', getName: function(){ // console.log("getName is name:",this.name) return this.name } } const FA = objB.getName console.log(FA()) // undefined,為什么呢,FA執行作用域是window,即getName函數作用域this===window,而在window.name可是沒有值的。 console.log(FA.bind(objB)()) // vvmily ,將objB作用域作為返回新函數體的執行環境 console.log(objB.getName()) // vvmily ,此時執行作用域是objB對象內,getName執行環境是objB作用域內,即this===objB。 FA.bind(obj) ``` ## 手動實現 目的:最終肯定返回一個函數體(如:myBind) ### 用FA.bind(objB)()分析: 1. 當FA.bind(objB)時,需要干點什么呢?肯定要保存objB作用域的數據 2. 該函數體需要包含哪些數據呢?包含FA.bind(objB)執行時的**執行作用域**和**入參**; 3. 而最終返回的函數體,執行時,還能訪問到上次FA.bind(objB)函數中的變量,則需要用到**閉包**了; 4. 接下來通過函數體如何訪問objB信息?這里需要借助一個中間構造函數Fn了,通過Fn原型繼承FA.bind(objB)的原型,即Fn.prototype = self.prototype; 5. 返回函數體原型繼承Fn實例,即myBind.prototype = new Fn()。 注意:FA.bind(objB)就是objB的作用域,訪問的就是objB數據。 ``` js function MyBind(context,...args){ let self = this; // 2 args = args || []; // 2 let Fn = function(){}; // 4 let myBind = function(){ // ... } Fn.prototype = self.prototype // 4 myBind.prototype = new Fn() // 5 return myBind } ``` ### 實現myBind函數體 * 這里需要借助前面實現的call或者apply方法 ``` js // ... let myBind = function(...params){ const allArgs = [...args, ...params] // 參數合并 return self.call(context, ...allArgs) } // ... ``` * 完整代碼 ``` js function MyBind(context,...args){ let self = this; args = args || []; let Fn = function(){}; let myBind = function(...params){ const allArgs = [...args, ...params] // 參數合并 return self.call((this instanceof Fn ? this : context), ...allArgs) } Fn.prototype = self.prototype myBind.prototype = new Fn() return myBind } ``` ## 最終總結 call、apply 和 bind 的功能相似,什么時候使用 bind 呢?這個確實也沒有明確的規定,只要知道其原理,怎么選擇都不重要,主要的區別無非就是 call、apply 綁定后是立即執行,而 bind 綁定后是返回函數體,需要調用即可。
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看