Lodash源码阅读-copySymbolsIn

Lodash 源码阅读-copySymbolsIn

概述

copySymbolsIn 是 Lodash 库中的一个内部工具函数,主要用于将源对象的自身和继承的可枚举 Symbol 属性复制到目标对象中。它是对象复制操作中处理 Symbol 类型属性的重要组成部分,特别是在需要考虑继承属性的深度克隆中发挥作用。

前置学习

依赖函数

  • copyObject:一个复制对象属性的基础函数,将源对象的属性复制到目标对象
  • getSymbolsIn:获取对象自身和继承的可枚举 Symbol 属性的函数,会遍历整个原型链
  • Object 构造器:在未提供目标对象时用于创建空对象

技术知识

  • ES6 Symbol:JavaScript 中的原始数据类型,用作对象属性的唯一标识符
  • 原型链(Prototype Chain):JavaScript 对象继承机制,对象可以从原型链继承属性和方法
  • 对象复制:JavaScript 中对象的浅拷贝和深拷贝概念与实现方式
  • 属性描述符:JavaScript 中对象属性的特性,如可枚举性、可写性等

源码实现

javascript 复制代码
/**
 * Copies own and inherited symbols of `source` to `object`.
 *
 * @private
 * @param {Object} source The object to copy symbols from.
 * @param {Object} [object={}] The object to copy symbols to.
 * @returns {Object} Returns `object`.
 */
function copySymbolsIn(source, object) {
  return copyObject(source, getSymbolsIn(source), object);
}

实现思路

copySymbolsIn 函数的实现思路非常直接明了:

  1. 调用 getSymbolsIn(source) 获取源对象及其原型链上的所有可枚举 Symbol 属性
  2. 将这些 Symbol 属性作为要复制的属性列表,传递给 copyObject 函数
  3. copyObject 函数负责将这些 Symbol 属性从源对象复制到目标对象
  4. 最终返回修改后的目标对象

这种实现方式利用了函数组合的思想,将获取 Symbol 和复制属性的功能分离,使代码更简洁清晰。

源码解析

函数签名

javascript 复制代码
function copySymbolsIn(source, object) {

函数接收两个参数:

  • source:源对象,要从中复制 Symbol 属性的对象
  • object:目标对象,要将 Symbol 属性复制到的对象(可选)

如果不提供 object 参数,copyObject 函数会创建一个新的空对象。

函数体

javascript 复制代码
return copyObject(source, getSymbolsIn(source), object);

这行代码包含了函数的全部逻辑,可以分解为以下步骤:

  1. getSymbolsIn(source):调用 getSymbolsIn 函数,获取源对象及其原型链上的所有可枚举 Symbol 属性数组
  2. copyObject(source, symbolsArray, object):调用 copyObject 函数,将获取到的 Symbol 属性从源对象复制到目标对象
    • source:源对象,提供属性值
    • symbolsArray:要复制的属性数组,这里是所有 Symbol 属性
    • object:目标对象,接收复制的属性

copyObject 函数的工作方式是遍历提供的属性数组(这里是 Symbol 属性数组),将每个属性从源对象复制到目标对象,并返回修改后的目标对象。

与 copySymbols 的对比

copySymbolsIncopySymbols 的主要区别在于:

javascript 复制代码
// copySymbols 仅复制对象自身的 Symbol 属性
function copySymbols(source, object) {
  return copyObject(source, getSymbols(source), object);
}

// copySymbolsIn 复制对象自身和继承的 Symbol 属性
function copySymbolsIn(source, object) {
  return copyObject(source, getSymbolsIn(source), object);
}

区别仅在于使用 getSymbols 还是 getSymbolsIn 来获取 Symbol 属性:

  • getSymbols 只获取对象自身的可枚举 Symbol 属性
  • getSymbolsIn 获取对象自身和继承的可枚举 Symbol 属性

这种区别对应了 JavaScript 中浅拷贝和深拷贝的不同需求。

总结

copySymbolsIn 函数是 Lodash 中一个短小精悍但功能强大的工具函数,它通过组合使用 getSymbolsIncopyObject 两个函数,实现了对象自身和继承的 Symbol 属性的复制。

这个函数的实现体现了几个软件设计原则:

  1. 单一职责原则:函数只负责一件事------复制 Symbol 属性,而获取 Symbol 和实际的复制操作则委托给其他专门的函数
  2. 函数组合 :通过组合 getSymbolsIncopyObject 这两个基础函数来构建更复杂的功能
  3. 抽象合理:提供了适当级别的抽象,使调用者不需要关心 Symbol 属性的获取和复制细节
  4. 接口一致性 :与 copySymbols 函数保持一致的接口,方便开发者在不同场景下选择合适的工具

在现代 JavaScript 开发中,随着 Symbol 的广泛使用,特别是在框架和库的内部实现中,copySymbolsIn 这样的工具函数变得越来越重要,它确保了在处理对象时不会遗漏这些特殊的属性,包括那些来自原型链的属性。

相关推荐
xiaofeichaichai3 小时前
Webpack
前端·webpack·node.js
问心无愧05133 小时前
ctf show web入门111
android·前端·笔记
唐某人丶3 小时前
模型越来越强,我们还需要 Agent 工程吗?—— 从价值重估到 Harness 实践
前端·agent·ai编程
智码看视界4 小时前
现代Web开发基础:全栈工程师的起航点
前端·后端·c5全栈
JS菌4 小时前
手写一个 AI Agent 全栈项目:从沙箱执行到子智能体的完整实现
前端·人工智能·后端
excel5 小时前
HLS TS 文件损坏的元凶:Git 提交与拉取
前端
Aphasia3115 小时前
https连接传输流程
前端·面试
徐小夕5 小时前
万字长文!千万级文档 RAG 知识库系统落地实践
前端·算法·github
threelab5 小时前
Three.js 物理模拟着色器 | 三维可视化 / AI 提示词
开发语言·前端·javascript·人工智能·3d·着色器