函数的 length 属性
Function.prototype.length 返回函数定义时的形参数量,不包括默认参数和剩余参数,常用于柯里化和函数式编程。
#resource / javascript
#resource / ecmascript
#type / concept
#status / evergreen
[!info] related notes
- 所属 MOC: ecmascript-moc
- 前置概念: ecmascript-functions
- 相关概念: currying, rest-parameters-and-spread-operator, call-apply-bind
函数的 length 属性
一句话定义
Function.prototype.length 返回函数定义时的形参数量(参数个数),不包括有默认值的参数和剩余参数。
核心机制
基本行为
function fn(a, b, c) {}
console.log(fn.length); // 3
function fn2(a, b, c = 1) {}
console.log(fn2.length); // 2
function fn3(...args) {}
console.log(fn3.length); // 0
关键规则
- 只计算形参:不计算实际传入的参数数量
- 不包括默认参数:有默认值的参数不计入
- 不包括剩余参数:
...rest参数不计入 - 从第一个有默认值的参数开始停止计数
详细示例
// 1. 普通函数
function add(a, b) { return a + b; }
console.log(add.length); // 2
// 2. 有默认值的参数
function greet(name, greeting = 'Hello') {
return `${greeting}, ${name}`;
}
console.log(greet.length); // 1
// 3. 剩余参数
function sum(...numbers) {
return numbers.reduce((a, b) => a + b, 0);
}
console.log(sum.length); // 0
// 4. 混合情况
function mixed(a, b = 1, c, d = 2) {
return a + b + c + d;
}
console.log(mixed.length); // 1(从第一个默认参数 b 开始停止计数)
// 5. 箭头函数
const arrowFn = (a, b, c) => a + b + c;
console.log(arrowFn.length); // 3
// 6. bind() 返回的函数
const boundFn = add.bind(null, 1);
console.log(boundFn.length); // 1(剩余参数数量)
实际应用
1. 柯里化实现
在实现柯里化函数时,length 属性用于判断何时参数已经足够:
function curry(fn) {
return function curried(...args) {
if (args.length >= fn.length) {
return fn.call(this, ...args);
}
return curried.bind(this, ...args);
};
}
const add = (a, b, c) => a + b + c;
console.log(add.length); // 3
const curriedAdd = curry(add);
curriedAdd(1)(2)(3); // 6
2. 参数验证
可以用于验证函数调用时是否传入了足够数量的参数:
function validateArgs(fn, ...args) {
if (args.length < fn.length) {
throw new Error(`需要 ${fn.length} 个参数,但只传入了 ${args.length} 个`);
}
return fn(...args);
}
3. 函数签名分析
可以用于分析函数的参数数量:
function analyzeFunction(fn) {
return {
name: fn.name,
parameterCount: fn.length,
isVariadic: fn.length === 0 && fn.toString().includes('...')
};
}
常见误解
1. 与 arguments.length 的区别
function fn(a, b) {
console.log(fn.length); // 2(定义时的形参数量)
console.log(arguments.length); // 3(调用时的实参数量)
}
fn(1, 2, 3);
2. 箭头函数没有 arguments
const arrowFn = (a, b) => {
// console.log(arguments); // ReferenceError: arguments is not defined
console.log(arrowFn.length); // 2
};
3. 默认参数的影响
// ❌ 错误理解:认为是 3
function fn(a, b = 1, c) {}
console.log(fn.length); // 1
// ✅ 正确理解:从第一个默认参数开始停止计数
// fn.length 只计算 a,不计算 b 和 c
BFE.dev 相关题目
- 1. implement curry():使用
fn.length判断参数数量 - 19. this:理解函数调用时的参数传递
面试要点
- 基本概念:知道
length返回定义时的形参数量 - 默认参数:理解默认参数不计入
length - 剩余参数:理解剩余参数不计入
length - 柯里化应用:知道如何在柯里化中使用
length - 与 arguments.length 的区别:能区分两者