Lodash源码阅读-copyArray

Lodash 源码阅读-copyArray

概述

copyArray 是 Lodash 中的一个内部工具函数,用于复制数组的所有元素到一个新数组或指定的目标数组中。它实现了数组的浅拷贝(shallow copy),即只复制数组元素的引用,而不是深度复制数组元素的内容。

前置学习

依赖函数

copyArray 是一个相对独立的基础函数,不依赖其他 Lodash 函数。

源码实现

javascript 复制代码
/**
 * Copies the values of `source` to `array`.
 *
 * @private
 * @param {Array} source The array to copy values from.
 * @param {Array} [array=[]] The array to copy values to.
 * @returns {Array} Returns `array`.
 */
function copyArray(source, array) {
  var index = -1,
    length = source.length;

  array || (array = Array(length));
  while (++index < length) {
    array[index] = source[index];
  }
  return array;
}

实现思路

copyArray 函数的实现思路非常直观:

  1. 接收两个参数:源数组 source 和目标数组 array(可选)
  2. 如果没有提供目标数组,则创建一个与源数组长度相同的新数组
  3. 使用循环遍历源数组的每个元素,将其复制到目标数组的相应位置
  4. 返回目标数组

源码解析

参数处理

javascript 复制代码
var index = -1,
  length = source.length;

array || (array = Array(length));

这段代码首先定义了两个变量:

  • index:初始化为 -1,用于跟踪当前处理的数组索引
  • length:源数组的长度

然后检查是否提供了目标数组 array:

  • 如果 array 为假值(如 undefined 或 null),则创建一个新数组
  • 新数组的长度与源数组相同,使用 Array(length) 预分配空间

这里使用了 JavaScript 的短路逻辑运算符 ||,如果 array 为假值,则执行右侧的表达式。这是一种常见的设置默认值的简洁方式。

数组复制

javascript 复制代码
while (++index < length) {
  array[index] = source[index];
}

这是函数的核心逻辑,使用 while 循环遍历源数组的每个元素:

  • 循环从索引 0 开始(因为 index 初始值为 -1,第一次 ++index 后变为 0)
  • 循环继续,直到处理完源数组中的所有元素(index < length 不再成立)
  • 每次迭代,将源数组的当前元素 source[index] 复制到目标数组的相应位置 array[index]

这种手动复制的方式比使用 Array.prototype.slice() 或展开运算符 [...source] 更直接,在某些情况下可能更高效,特别是当需要复制到现有数组而不是创建新数组时。

返回结果

javascript 复制代码
return array;

函数最后返回目标数组,无论是新创建的还是传入的。这使得函数可以链式调用,也符合 Lodash 的一般设计风格。

总结

copyArray 函数虽然简单,但它体现了几个重要的编程原则:

  1. 单一职责原则:

    • 函数只做一件事:复制数组元素
    • 实现简单明了,易于理解和维护
  2. 灵活性:

    • 支持复制到新数组或现有数组
    • 通过参数控制行为,而不是硬编码
  3. 性能考虑:

    • 预分配数组大小,避免动态增长带来的性能开销
    • 使用基本的循环而不是高阶函数,在某些情况下可能更高效
  4. 代码复用:

    • 作为基础工具函数,被多个高级函数使用
    • 避免在多个地方重复实现相同的逻辑

虽然现代 JavaScript 提供了多种数组复制方法(如 Array.prototype.slice()、[...array] 展开语法、Array.from(array) 等),但 copyArray 的实现方式仍然有其价值,特别是在需要精确控制复制过程或复制到现有数组时。

相关推荐
Ai-_Man33 分钟前
您您这可以把Grok的多个会话比如说。左侧的多个会话一次性导出吗?不是单条会话里面的多次会对话。AI导出鸭
javascript·人工智能·ai·小程序·电脑
传人once37 分钟前
多图片上传预览功能如何写
前端·css·html·jquery·html5
Eric.461 小时前
Wan‑Animate+MiniMax-H3 本地部署 AI 漫剧流水线:8G 显存动作迁移与动态分镜工程实战
前端·人工智能·comfyui·ai漫剧
liangshanbo12151 小时前
JavaScript 异步核心主线
javascript·事件循环·异步操作
传人once2 小时前
悬停旋转放大和位移效果如何写
javascript·css·动画
库拉镜像AI牛牛3 小时前
短剧内容自动化生产:知漫剧工作室落地教程
大数据·服务器·前端·人工智能·语音识别
律宏阔3 小时前
Flutter 列表图片内存优化:CachedNetworkImage 与 ClipRRect 的取舍
前端·flutter
行者全栈架构师3 小时前
【鸿蒙心迹】相册文搜图工程化落地:HarmonyOS 7.0 端侧 AI 检索全链路实战与 5 个踩坑解法
前端
律宏阔3 小时前
Dart 3 Record:解决 Future.wait 异构返回值的类型问题
前端·flutter
Seraphina363 小时前
DVWA(XSS Reflected/Stored High,CSRF Low)
前端·xss·csrf