十年匠心定制 · 商业建站与技术教学双线并行 咨询热线:400-886-1026 service@lmnt.cn
ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

es-toolkit set 函数指南:动态路径写入对象,lodash 迁移三步上手

es-toolkit set 函数指南:动态路径写入对象,lodash 迁移三步上手 es-toolkit set 函数指南动态路径写入对象lodash 迁移三步上手【免费下载链接】es-toolkitA modern JavaScript utility library thats 2-3 times faster and up to 97% smaller, a major upgrade to lodash.项目地址: https://gitcode.com/GitHub_Trending/es/es-toolkites-toolkit 兼容层的set函数解决一个具体问题按字符串路径向嵌套对象写入值路径缺失的中间层级会自动创建。它是 lodash_.set的直接替代也是动态路径场景下省掉手写递归的工具。为什么需要它两个真实困境你可能遇到过这种代码路径来自配置或用户输入obj[path] value对a.b.c这种深路径无能为力——中间层不存在赋值直接报TypeError。另一个场景更普遍从 lodash 迁移时_.set的调用点散落在几十处逐个改成原生赋值既不现实也不安全需要一个行为逐字节对齐的替身。es-toolkit/compat里的set就是为此准备的行为细节稀疏数组、原型污染拦截等与 lodash 保持一致。快速上手三个最小示例最基础的用法是嵌套写入中间层不存在就自动补齐import { set } from es-toolkit/compat; const user {}; set(user, profile.address.city, Shanghai); // user { profile: { address: { city: Shanghai } } }路径不必是点号字符串。数组形式的路径每段原样使用不会被 join 成a,b,c这样的字面键名数字段则按数组下标处理const list {}; set(list, items[0], first); set(list, items[2], third); // list.items [first, 1 empty item, third]跳号写items[2]会留下空位得到稀疏数组——这是与 lodash 对齐的细节也是后文要提醒的坑。迁移 lodash 的代码则是一行替换// 迁移前 import _ from lodash; _.set(data, pathFromConfig, payload); // 迁移后 import { set } from es-toolkit/compat; set(data, pathFromConfig, payload);先读两个反直觉它改的是原对象且返回同一个引用。测试里对set(object, a, 2)的断言是expect(actual).toBe(object)见 src/compat/object/set.spec.tstoBe验的是引用相等。如果你的代码假设拿到的是新对象副作用会沿引用扩散——需要不可变更新时请改走解构。其余三个不显眼的行为nullish 输入安静返回set(null, a.b, 1)返回nullset(undefined, ...)返回undefined不抛错src/compat/object/set.spec.ts。好处是链式调用不怕空对象坏处是拼错变量名时错误被静默吞掉。数字下标自动建数组其他键建对象set({}, a[1].b.c, 2)得到{ a: [undefined, { b: { c: 2 } }] }src/compat/object/set.spec.ts。只有严格非负整数的键才算下标[1a, 2b, 3c]这种数字开头但不是纯数字的键前缀不会触发数组。原型污染路径直接拦截路径段是__proto__、constructor或prototype时函数原样返回、不写入任何东西src/_internal/isUnsafeToWriteProperty.ts。set({}, __proto__.polluted, 1)什么都不会发生。原理速览一次写入走了哪几步结论先说set本体只有 6 行它把新值包成恒定 updater 后整体委托给 updateWithreturn updateWith( obj, path, () value, () undefined );把set想成一个快递员内部流程可以概括为四步解析地址。单个键直接使用数组按段逐一走字符串则交给toPath拆解src/compat/util/toPath.ts——点号、括号a[0].b、引号包裹的a[b.c]都能正确切分引号内的点不会拆断。逐段安检。每段键先过 isUnsafeToWriteProperty命中风险键立即返回原对象写入中止。逐段铺路。中间节点优先复用已存在的对象缺失时若下一段是数组下标就建[]否则建{}判断逻辑见 isIndex。落货。最后一段写入 updater 算好的值新旧值相等时直接跳过赋值避免触发多余的 settersrc/compat/_internal/assignValue.ts。顺带说明性能问题。官方文档原话是这个set内部调用updateWith因复杂的路径处理和对象创建逻辑运行较慢建议改用直接赋值或解构赋值docs/compat/reference/object/set.md。选它图的是兼容性而非速度es-toolkit 的整体优势在别处——对比图中同尺寸下 es-toolkit 的体积明显更小、吞吐更高该用它还是用原生语法场景建议路径来自配置、用户输入运行时才确定用set避免手写递归建链从 lodash 迁移需要行为完全对齐用set直接替换_.set路径是静态的a.b.c原生obj.a.b.c v更快更直观需要不可变更新解构展开或 immutable 类库只需读取不需要写入可选链obj?.a?.b或兼容层的get一句话收束set的价值在于动态路径能力和 lodash 行为等价而不是性能。如果默认的数字段建数组、其余建对象策略不够用可以看 setWith配套的读取函数是 get。【免费下载链接】es-toolkitA modern JavaScript utility library thats 2-3 times faster and up to 97% smaller, a major upgrade to lodash.项目地址: https://gitcode.com/GitHub_Trending/es/es-toolkit创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表