为精进js的水平,所以计划阅读lodash源码,故开此计划:每日lodash,每日阅读一个lodash源码,并讲解源码的内容。
chunk
今天的源码为lodash的第一个方法,_.chunk
先看源码:
function chunk(array, size = 1) {
size = Math.max(toInteger(size), 0)
const length = array == null ? 0 : array.length
if (!length || size < 1) {
return []
}
let index = 0
let resIndex = 0
const result = new Array(Math.ceil(length / size))
while (index < length) {
result[resIndex++] = slice(array, index, (index += size))
}
return result
}
这里一共有两个外面的方法,一个是toInterger,另一个是slice。 toInterger主要将传入进来的size变成整数,因为数组的分段不能进行负数分段,所以一进来函数就要处理size,使得size为大于或等于0的整数。
然后会进行传入数组的判断,如果传入的数组是null,就会将length赋0,否则赋数组的长度。
将不符合的参数进行检测,如果不通过检测,就返回一个空数组。
Math.ceil是向上取整的函数。
let index = 0
let resIndex = 0
const result = new Array(Math.ceil(length / size))
这里是初始化处理的参数:
index是处理函数分段的开始索引,一开始为0
resIndex是得到结果的函数的索引,开始也为0
result就是我们要返回的结果的数组,他的长度是(传入数组长度/传入分段的长度)向上取整。
然后进行循环遍历:
while (index < length) {
result[resIndex++] = slice(array, index, (index += size))
}
slice是返回array的index索引处开始(包含),index+=size索引处结束(不包含)的子数组,所以每循环一次就会将一个片段放入result里面
当index>=length时候跳出循环, [a,b,c,d,e,f,g] 这个数组长度为7,如果我们将其分为3个一份,一开始:index=0,resIndex=0,result=[] 循环完第一次 index=3,resIndex=1,result=[[a,b,c]] 循环完第二次 index=6,resIndex=2,result=[[a,b,c],[d,e,f]] 此时我们可以看到index<length => 6<7的,所以会进入最后一层循环,将最后一个g放入result = [[a,b,c],[d,e,f],[g]],然后将result返回就结束这个函数了。