解析Array.prototype.slice.call(arguments)
标签:
JavaScript
在es5标准中,我们经常需要把arguments对象转换成真正的数组
1 // 你可以这样写2 var arr = Array.prototype.slice.call(arguments)3 4 // 你还可以这样写5 var arr = [].slice.call(arguments)6 7 // 你要是不怕麻烦,你还可以这样写8 var arr = [].__proto__.slice.call(arguments)
以上三种写法是等价的。
1 // 当你了解原型链,你就知道2 Array.prototype === [].__proto__ // true3 4 // [].slice调用的是实例[]的原型对象中的slice方法5 [].slice === [].__proto__.slice // true
Array.prototype.slice.call(arguments)原本调用slice的是Array.prototype,而call(arguments)使得调用slice方法的对象改成arguments,你可以想象成
Array.prototype.slice.call(arguments) ~ arguments.slice()
Array.prototype.slice.call(arguments, [begin[, end]]) ~ arguments.slice([begin [, end]])
我们可能会想arguments原型对象是Object.prototype,并没有slice方法,slice方法从哪里来?
这是因为call(arguments)不仅是改变了this的指向,还使得arguments对象继承了Array.prototype中的slice方法。
下面是Array.prototype.slice()源码:指路github地址 587行
function ArraySlice(start, end) { CHECK_OBJECT_COERCIBLE(this, "Array.prototype.slice"); var array = TO_OBJECT(this); var len = TO_LENGTH(array.length); var start_i = TO_INTEGER(start); var end_i = len; if (!IS_UNDEFINED(end)) end_i = TO_INTEGER(end); if (start_i < 0) { start_i += len; if (start_i < 0) start_i = 0; } else { if (start_i > len) start_i = len; } if (end_i < 0) { end_i += len; if (end_i < 0) end_i = 0; } else { if (end_i > len) end_i = len; } var result = ArraySpeciesCreate(array, MaxSimple(end_i - start_i, 0)); if (end_i < start_i) return result; if (UseSparseVariant(array, len, IS_ARRAY(array), end_i - start_i)) { %NormalizeElements(array); if (IS_ARRAY(result)) %NormalizeElements(result); SparseSlice(array, start_i, end_i - start_i, len, result); } else { SimpleSlice(array, start_i, end_i - start_i, len, result); } result.length = end_i - start_i; return result; }
arguments可以转换为数组对象也是因为
我们可以看到arguments对象成员属性类似数组,且有length属性,那是不是这样类似的对象都可以调用slice呢,我们试验一下
1 var obj = {2 0: 'foo',3 1: 'bar',4 2: 'arg',5 length: 36 }7 console.log(Array.prototype.slice.call(obj))8 // ["foo", "bar", "arg"]
这是可以的!
*PS:es6语法中新增了Array.from(),所以上述类型的对象可以Array.from(obj)就直接转化成数组!
作者:三目鱼的池塘
原文出处:https://www.cnblogs.com/threeEyes/p/10478762.html
点击查看更多内容
1人点赞
评论
共同学习,写下你的评论
评论加载中...
作者其他优质文章
正在加载中
感谢您的支持,我会继续努力的~
扫码打赏,你说多少就多少
赞赏金额会直接到老师账户
支付方式
打开微信扫一扫,即可进行扫码打赏哦