首先call和apply的作用是一樣的含蓉,只是傳參數(shù)的方式不同而已,舉個例子
var arr1 = [1,2,3];
Array.prototype.push.apply(arr1,[4,5,6])
//Array.prototype.push.call(arr1,4,5,6)
call和apply的實現(xiàn)原理都是改變參數(shù)中的對象指向歧胁,指向調(diào)用call或apply的Function對象中的this
function person(name){
this.name = name
}
function male(){}
var male1 = new male()
person.call(male1,"xujizhong")
male1.name//"xujizhong"
上面代碼中將male這個對象指向了person中的this舟肉,所以相當于運行了 male.name = name,而call中傳入了參數(shù)"xujizhong",所以male1.name的輸出結(jié)果為"xujizhong"
比較經(jīng)典的例子像Array.prototype.slice.call(arguments)燕酷,可以將類數(shù)組轉(zhuǎn)換成數(shù)組(類數(shù)組必須包含length屬性)
var arr2 = {1: 1, 2: 2, 5: 5, aa: "aa", length: 10}
var arr3 = Array.prototype.slice.call(arr2)
//[empty, 1, 2, empty × 2, 5, empty × 4]
//1:1
//2:2
//5:5
//length:10
arr[0] //undefined
arr[1] //1
Array.prototype.slice方法將對象中的非索引的對象刪除并且對應length在沒有索引的位置加入了空位置籍凝,并且因為slice方法返回的是數(shù)組,所以獲得的arr3為一個數(shù)組
也可以利用Array.prototype.filter從不返回稀疏數(shù)組的特性來獲得一個非稀疏數(shù)組的數(shù)組
var arr2 = {1: 1, 2: 2, 5: 5, aa: "aa", length: 10}
var arr4 = Array.prototype.filter.call(arr2,function(){return true})
// [1, 2, 5]
//0:1
//1:2
//2:5
//length:3