溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

JavaScript中bind、call、apply方法怎么使用

發布時間:2022-05-05 09:59:47 來源:億速云 閱讀:218 作者:iii 欄目:開發技術

這篇文章主要講解了“JavaScript中bind、call、apply方法怎么使用”,文中的講解內容簡單清晰,易于學習與理解,下面請大家跟著小編的思路慢慢深入,一起來研究和學習“JavaScript中bind、call、apply方法怎么使用”吧!

call的基本使用

var ary = [12, 23, 34];
ary.slice();

以上兩行簡單的代碼的執行過程為:ary這個實例通過原型鏈的查找機制找到Array.prototype上的slice方法,讓找到的slice方法執行,在執行slice方法的過程中才把ary數組進行了截取。

注意slice方法執行之前有一個在原型上查找的過程(當前實例中沒有找到,再根據原型鏈查找)。

當知道了一個對象調用方法會有一個查找過程之后,我們再看:

var obj = {name:'iceman'};
function fn() {
    console.log(this);
    console.log(this.name);
}
fn(); // this --> window
// obj.fn(); // Uncaught TypeError: obj.fn is not a function
fn.call(obj);

call方法的作用:首先尋找call方法,最后通過原型鏈在Function的原型中找到call方法,然后讓call方法執行,在執行call方法的時候,讓fn方法中的this變為第一個參數值obj,最后再把fn這個函數執行。

知道這個原型上的原理后,咱們就可以動手分析實現這三個方法了。

bind、call、apply 區別

  • call 和 apply 都是為了解決改變 this 的指向。作用都是相同的,只是傳參的方式不同。

  • 除了第一個參數外,call 可以接收一個參數列表,apply 只接受一個參數數組

let a = {
    value: 1
}
function getValue(name, age) {
    console.log(name)
    console.log(age)
    console.log(this.value)
}
getValue.call(a, 'yck', '24')
getValue.apply(a, ['yck', '24'])

bind 和其他兩個方法作用也是一致的,只是該方法會返回一個函數。并且我們可以通過 bind 實現柯里化

如何實現一個 bind 函數

對于實現以下幾個函數,可以從幾個方面思考

  • 不傳入第一個參數,那么默認為 window

  • 改變了 this 指向,讓新的對象可以執行該函數。那么思路是否可以變成給新的對象添加一個函數,然后在執行完以后刪除?

當然是肯定的,于是我們可以這樣寫:

Function.prototype.myBind = function (context) {
  if (typeof this !== 'function') {
    throw new TypeError('Error')
  }
  var _this = this
  var args = [...arguments].slice(1)
  // 返回一個函數
  return function F() {
    // 因為返回了一個函數,我們可以 new F(),所以需要判斷
    if (this instanceof F) {
      return new _this(...args, ...arguments)
    }
    return _this.apply(context, args.concat(...arguments))
  }
}

如何實現一個 call 函數

Function.prototype.myCall = function (context,...arg) {
  var context = context || window  // 給 context 添加一個屬性
  // getValue.call(a, 'yck', '24') => a.fn = getValue
  //使用symbol 選擇一個獨一無二的值作為新添加的屬性
  let symbol = new Symbol();
  context[symbol] = this;
  let result = context[symbol](...arg)
  // 刪除添加的函數
  delete context[symbol]  
  return result
}

如何實現一個apply 函數

apply實現原理與call實現基本類似,只有傳值的方式不一樣。

Function.prototype.myApply = function (context,arg) {
  var context = context || window // 給 context 添加一個屬性
 // getValue.call(a, 'yck', '24') => a.fn = getValue
 //使用symbol 選擇一個獨一無二的值作為新添加的屬性
 let symbol = new Symbol();
 context[symbol] = this;
 let result = context[symbol](arg)
 // 刪除添加的函數
 delete context[symbol]
 return result
}

經過對以上的函數進行檢測 , 完美通過。

const obj = {  
 name : 'xiaoxiao',  
 getName : function (arg) {  
 console.log(`我是${this.name}里面的,我里面有${arg}`);  
 }  
}  
obj.getName([0,0,0,0,0]); // 我是xiaoxiao里面的  
const obj2 = {  
 name : 'huahua'  
}  
//傳值不一樣  
obj.getName.myCall(obj2,1,1,1,1,1,1);  
obj.getName.myBind(obj2)(2,2,2,2,2,2);  
obj.getName.myApply(obj2,[3,3,3,3,3,3]);

感謝各位的閱讀,以上就是“JavaScript中bind、call、apply方法怎么使用”的內容了,經過本文的學習后,相信大家對JavaScript中bind、call、apply方法怎么使用這一問題有了更深刻的體會,具體使用情況還需要大家實踐驗證。這里是億速云,小編將為大家推送更多相關知識點的文章,歡迎關注!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

亚洲午夜精品一区二区_中文无码日韩欧免_久久香蕉精品视频_欧美主播一区二区三区美女