es-toolkit 兼容版 `ary` 函数完全指南:限制函数参数个数、修复 `map(parseInt)` 陷阱
es-toolkit 兼容版ary函数完全指南限制函数参数个数、修复map(parseInt)陷阱【免费下载链接】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导读本文围绕 es-toolkit 兼容层es-toolkit/compat提供的ary函数展开讲解如何创建一个只接收最多n个参数的新函数从而安全使用回调函数、规避数组方法隐式传入多余参数如经典的[1,2,3].map(parseInt)返回[1, NaN, NaN]陷阱等常见问题。读完本文你将掌握ary(func, n)的完整用法、参数边界行为负数、NaN、省略n时的默认值、它与现代版ary及unary的关系以及其底层源码实现原理。说明本文主体基于仓库文档 docs/ja/compat/reference/function/ary.md及其英文对应版 docs/compat/reference/function/ary.md展开并补充对应源码与测试作为佐证。先读警告优先使用现代版ary关联文档开篇即以醒目的警告块提示读者es-toolkit兼容版ary函数因包含复杂的参数验证逻辑运行速度较慢。请改用更快、更现代的 es-toolkit 原生 ary 函数。这意味着在 es-toolkit 中存在两条 API 路径es-toolkit/function下的 ary轻量、快速仅做纯粹的参数截断es-toolkit/compat下的ary面向 lodash 行为兼容作为 lodash 的 drop-in replacement多出类型守卫、负数/NaN归一化、guard参数等校验逻辑因此更慢。如果追求性能且不需要 lodash 兼容行为请优先从es-toolkit/function导入ary如果你的项目正在从 lodash 迁移、依赖 lodash 的边界语义则使用es-toolkit/compat版本。ary是什么限制函数可接收的参数个数ary创建一个新函数该函数调用原函数时只传递最多n个参数其余参数一律忽略const cappedFunction ary(func, n);典型使用场景包括安全地使用接收参数过多的函数在回调函数中忽略数组方法如map、filter、forEach隐式传入的额外参数索引、原数组等在函数式编程中约束函数元数arity。使用法ary(func, n)基础用法截断多余参数当你希望限制某个函数只接收指定数量的参数时使用aryimport { ary } from es-toolkit/compat; // 基础使用法 function greet(name, age, city) { return こんにちは、${name}さん! ${age}歳、${city}からいらっしゃいました。; } const limitedGreet ary(greet, 2); console.log(limitedGreet(田中, 30, 東京, 追加引数)); // こんにちは、田中さん! 30歳、undefinedからいらっしゃいました。 // 第 3 个参数及其之后的参数被忽略从上面的输出可以看到東京和追加引数均未进入函数体city参数得到的是undefined。实战场景修复map(parseInt)经典陷阱parseInt接受两个参数字符串与进制基数而map的回调会被传入三个参数当前元素、索引、原数组。直接传入parseInt时索引会被当作基数传入导致NaNimport { ary } from es-toolkit/compat; // parseInt 接受第 2 个参数基数但 map 的回调会传入 3 个参数 const numbers [1, 2, 3, 4, 5]; // 错误用法 —— parseInt 把索引当作基数接收 console.log(numbers.map(parseInt)); // [1, NaN, NaN, NaN, NaN] // 使用 ary 只传递第一个参数 console.log(numbers.map(ary(parseInt, 1))); // [1, 2, 3, 4, 5]这正是ary最经典的实战价值parseInt(2, 1)、parseInt(3, 2)等非法基数调用被彻底避免。对应测试见 src/compat/function/ary.spec.ts 中的should cap the number of arguments provided to func用例[6, 8, 10].map(ary(parseInt, 1))期望得到[6, 8, 10]。用不同的n精确控制参数数量ary允许你按需决定新函数接收几个参数import { ary } from es-toolkit/compat; function sum(...args) { return args.reduce((total, num) total num, 0); } const sum0 ary(sum, 0); const sum1 ary(sum, 1); const sum2 ary(sum, 2); const sum3 ary(sum, 3); console.log(sum0(1, 2, 3, 4, 5)); // 0 不传任何参数 console.log(sum1(1, 2, 3, 4, 5)); // 1 只传第一个参数 console.log(sum2(1, 2, 3, 4, 5)); // 3 只传前两个参数 console.log(sum3(1, 2, 3, 4, 5)); // 6 只传前三个参数注意ary只是限制上限并不会强制调用方必须传够n个参数。测试用例should not force a minimum argument count见 src/compat/function/ary.spec.ts验证了这一点即使调用时只传 0、1、2 个参数ary(fn, 3)也会如实转发。边界情况负数与NaN按 0 处理传入负数或NaN作为n时会被当作0处理即所有参数都被忽略import { ary } from es-toolkit/compat; const func (a, b, c) [a, b, c]; console.log(ary(func, -1)(1, 2, 3)); // [undefined, undefined, undefined] 负数按 0 处理 console.log(ary(func, NaN)(1, 2, 3)); // [undefined, undefined, undefined] NaN 按 0 处理参数与返回值参数funcFunction需要限制参数个数的原函数。nnumber可选允许的最大参数个数。省略时使用函数的length属性作为默认上限。返回值Function一个新函数调用时最多接收n个参数并返回原函数的结果。源码级原理兼容版ary的实现细节es-toolkit 兼容版的实现位于 src/compat/function/ary.ts其核心逻辑如下export function aryF extends (...args: any[]) any( func: F, n: number func.length, guard?: unknown ): (...args: any[]) ReturnTypeF { if (guard) { n func.length; } if (Number.isNaN(n) || n 0) { n 0; } return aryToolkit(func, n); }可以从中提炼出几个关键行为这些正是文档所述复杂参数验证的源码依据默认值取自func.lengthn的默认值是func.length函数的形参声明个数。因此ary(fn)不传n时等价于按函数自身元数截断。测试用例should use func.length if n is not given验证了ary(fn)调用fn(a,b,c,d)时只转发前 3 个参数见 src/compat/function/ary.spec.ts。guard参数lodash 兼容细节当传入第三个参数guard且为真值时n会被强制重置为func.length。这是为了兼容 lodash 中将ary直接作为_.map等方法的迭代器iteratee使用时的行为——lodash 会向ary额外传入一个 guard 值。测试用例should work as an iteratee for methods like _.map验证了[fn].map(ary)仍能正常工作。负数与NaN归一化为 0通过Number.isNaN(n) || n 0判断统一置为0与文档描述完全一致。数字强制转换n最终会经过aryToolkit的args.slice(0, n)处理。测试用例should coerce n to an integer验证了字符串1、小数1.6都会被截断语义处理1.6实际只取前 1 个参数而无法解析的xyz产生空参数列表。最终实际执行参数截断的是底层的aryToolkit即现代版实现 src/function/ary.tsexport function aryF extends (...args: any[]) any(func: F, n: number): (...args: any[]) ReturnTypeF { return function (this: any, ...args: ParametersF) { return func.apply(this, args.slice(0, n)); }; }现代版只做一件事用args.slice(0, n)截断参数列表并通过func.apply(this, ...)保留原函数的this绑定。测试用例should use this binding of function见 src/compat/function/ary.spec.ts验证了这一点ary生成的新函数作为对象方法调用时this正确指向该对象。对比可见兼容版 参数校验层默认值、guard、负数/NaN归一化 现代版截断内核。这也是文档警告兼容版因复杂参数验证而变慢的直接原因。与unary的关系ary(func, 1)在 es-toolkit 中被封装为专门的unary函数实现见 src/compat/function/unary.tsexport function unaryT, U(func: (arg1: T, ...args: any[]) U): (arg1: T) U { return ary(func, 1); }即unary是ary的特例只允许 1 个参数二者与ary(func, 0)一起构成了对函数元数的完整控制工具集。导出入口与使用前提兼容版ary通过 src/compat/compat.ts 从es-toolkit/compat导出export { ary } from ./function/ary.ts;因此使用时需从兼容入口导入import { ary } from es-toolkit/compat;需要说明的适用前提与限制本文代码示例依赖当前仓库文档所描述的 APIdocs/ja/compat/reference/function/ary.md、docs/compat/reference/function/ary.md与源码src/compat/function/ary.ts一致es-toolkit/compat的目标是成为 lodash 的 drop-in replacement见 src/compat/index.ts 顶部说明因此该版本刻意保留 lodash 的边界语义如 guard 迭代器行为、n省略时取func.length若你不需要 lodash 兼容语义且在意性能请改从es-toolkit/function导入 ary对应实现 src/function/ary.ts。小结ary是 es-toolkit 中控制函数元数的核心工具本文梳理了其兼容版的完整行为基础能力将函数参数截断到最多n个忽略多余参数经典实战修复map(parseInt)的NaN陷阱防止回调收到意外参数边界语义n省略时默认func.length负数、NaN一律按0处理数字自动转为整数语义原理支撑兼容版在 src/compat/function/ary.ts 中完成校验后委托现代版内核 src/function/ary.ts 执行截断并通过 src/compat/function/ary.spec.ts 覆盖全部边界行为性能取舍需要 lodash 兼容语义时使用es-toolkit/compat追求极致性能时优先使用es-toolkit/function的原生版本。【免费下载链接】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),仅供参考