在我的项目中,我注册了不同的函数(具有不同数量的参数)作为许多事件的监听器。当事件发生时,我需要触发相关的功能。我以数组的形式接收要传递给listener方法的参数,而listener函数期望每个单独的参数。所以,我这样做,但我不喜欢这种方法,并想知道是否有一种优雅的方式,
function callListenerWithArgs(func, args){
switch(args.length){
case 1:
func(args[0]);
break;
case 2:
func(args[0], args[1]);
break;
case 3:
func(args[0], args[1], args[2]);
break;
case 4:
func(args[0], args[1], args[2], args[3]);
break;
default:
func();
}
}
答案 0 :(得分:2)
使用.apply
func.apply(null, args)
如果需要绑定到特定范围,可以传入另一个参数以在函数内使用this
:
func.apply(scope, args);
此外,JavaScript的细微差别在于您可以使用未定义的值调用函数。因此,对现有代码进行小幅调整将在95%的情况下有效(这不是建议作为解决方案,只是指出来):
// will handle any number of args up to 7
function callListenerWithArgs(func, args){
func(args[0], args[1], args[2], args[3], args[4], args[5], args[6]);
}
如果您的func
定义为:
function foo(a, b, c){
}
您传入了a
,b
,c
以及一些被忽略的undefined
值。正如我上面所说,这在95%的情况下起作用。如果您检查被调用函数中的arguments.length
,它将无效,因为无论函数定义的参数数量是多少,它都将始终相同。
答案 1 :(得分:1)
function callListenerWithArgs(func, args){
func.apply(window, args);
}
答案 2 :(得分:1)
functionName.apply(thisScope, arguments)
会更优雅。 arguments
参数必须是数组。
您可以像以下一样构建数组:
var args = [];
switch (arguments.length - 1) {
case 0:
break;
case 1:
args.push(arguments[1]);
break;
case 2:
args.push(arguments[1], arguments[2]);
break;
case 3:
args.push(arguments[1], arguments[2], arguments[3]);
break;
default:
args = Array.prototype.slice.call(arguments, 1);
}
或者如果数组已经构建,只需将其作为第二个参数传递给.apply
答案 3 :(得分:1)
func.apply(this, args);
请参阅here。
答案 4 :(得分:-1)
您可以获取函数的参数数量:
var f = function ( ) { console.log(arguments.length); }
f( 2, 3 ) // > 2
这可让您直接实施func
功能。
function func() {
var nbArgs = arguments.length;
// ...
}