lodash源码阅读二:chunk,compact

471 阅读2分钟

参考资料

github仓库地址

源码拷贝仓库地址(阅读的源码版本)

中文文档

英文文档

chunk(array, size)

chunk 方法将数组 array 拆分成多个长度 size 的区块数组,并将这些返回由这些区块数组为元素组成的数组。如果 array 不能分成等长的数组,那么最后剩余的元素依然组成一个区块数组

例如

_.chunk(['a', 'b', 'c', 'd'], 2);
// => [['a', 'b'], ['c', 'd']]
 
_.chunk(['a', 'b', 'c', 'd'], 3);
// => [['a', 'b', 'c'], ['d']]

源码

slicetoInteger 源码可以查看上一篇阅读笔记 lodash源码阅读一

import slice from './slice.js'
import toInteger from './toInteger.js'

/**
 * 数组 `array` 拆分成多个长度 `size` 的区块数组
 * 并将这些返回由这些区块数组为元素组成的数组
 * 如果 `array` 不能分成等长的数组,那么最后剩余的元素依然组成一个区块数组
 *
 * @param {Array} array 被切割的数组
 * @param {number} [size=1] 区块的长度
 * @returns {Array} 返回新的数组
 * @example
 *
 * chunk(['a', 'b', 'c', 'd'], 2)
 * // => [['a', 'b'], ['c', 'd']]
 *
 * chunk(['a', 'b', 'c', 'd'], 3)
 * // => [['a', 'b', 'c'], ['d']]
 */
function chunk(array, size = 1) {
  size = Math.max(toInteger(size), 0)
  const length = array == null ? 0 : array.length
  // 如果数组长度为 0 或者切割大小小于 1,返回空数组
  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
}

export default chunk

compact(array)

compact 方法将传入的数组中所有为假值的元素(如 falsenull0"", undefined, 和 NaN)都过滤掉并返回新的数组

/**
 * 将传入的数组中所有为假值的元素都过滤掉并返回新的数组
 * `0`, `""`, `undefined`, and `NaN` are falsey.
 *
 * @param {Array} array 被筛选值得数组
 * @returns {Array} 返回筛选过后的新数组
 * @example
 *
 * compact([0, 1, false, 2, '', 3])
 * // => [1, 2, 3]
 */
function compact(array) {
  let resIndex = 0
  const result = []
  // 判断有无传入数组,没有直接返回空数组
  if (array == null) {
    return result
  }

  // 遍历数组,判断每个元素的值
  for (const value of array) {
    if (value) {
      result[resIndex++] = value
    }
  }
  // 返回结果
  return result
}

export default compact

在 lodash 中有许多像 array == null 这样判断值是否宽松等于 null 的代码,其主要作用就是判断目标值是否是 undefined 或者是 null。对此以及关于真值和假值的详细的讲解描述,可以看这篇文章林景宜的记事本,文章的作者对此做了详细的描述,网上也有很多讲解,这里就不做详述。