Tim*_*imo 510 javascript arguments function argument-passing
有没有办法允许JavaScript中的函数"无限"变量?
例:
load(var1, var2, var3, var4, var5, etc...)
load(var1)
Run Code Online (Sandbox Code Playgroud)
rou*_*tic 790
当然,只需使用该arguments对象.
function foo() {
for (var i = 0; i < arguments.length; i++) {
console.log(arguments[i]);
}
}
Run Code Online (Sandbox Code Playgroud)
Ram*_*ast 152
在最近的浏览器中,您可以使用以下语法接受可变数量的参数:
function my_log(...args) {
// args is an Array
console.log(args);
// You can pass this array as parameters to another function
console.log(...args);
}
Run Code Online (Sandbox Code Playgroud)
Ken*_*Ken 111
另一种选择是在上下文对象中传入您的参数.
function load(context)
{
// do whatever with context.name, context.address, etc
}
Run Code Online (Sandbox Code Playgroud)
并像这样使用它
load({name:'Ken',address:'secret',unused:true})
Run Code Online (Sandbox Code Playgroud)
这样做的好处是,您可以根据需要添加任意数量的命名参数,并且该函数可以根据需要使用它们(或不使用它们).
mbe*_*ley 45
我同意Ken的答案是最有活力的,我更愿意更进一步.如果它是一个用不同参数多次调用的函数 - 我使用Ken的设计但是然后添加默认值:
function load(context) {
var defaults = {
parameter1: defaultValue1,
parameter2: defaultValue2,
...
};
var context = extend(defaults, context);
// do stuff
}
Run Code Online (Sandbox Code Playgroud)
这样,如果您有许多参数但不一定需要在每次调用函数时设置它们,您只需指定非默认值即可.对于extend方法,您可以使用jQuery的extend方法($.extend()),自己制作或使用以下代码:
function extend() {
for (var i = 1; i < arguments.length; i++)
for (var key in arguments[i])
if (arguments[i].hasOwnProperty(key))
arguments[0][key] = arguments[i][key];
return arguments[0];
}
Run Code Online (Sandbox Code Playgroud)
这将将上下文对象与默认值合并,并使用默认值填充对象中的任何未定义值.
Can*_*var 18
是的,就像这样:
function load()
{
var var0 = arguments[0];
var var1 = arguments[1];
}
load(1,2);
Run Code Online (Sandbox Code Playgroud)
Nic*_*tti 16
正如Ramast指出的那样,最好使用rest参数语法.
function (a, b, ...args) {}
Run Code Online (Sandbox Code Playgroud)
我只是想添加... args参数的一些不错的属性
- 它是一个数组,而不是像参数这样的对象.这允许您直接应用地图或排序等功能.
- 它不包括所有参数,只包括从中传递的参数.例如,在这种情况下,函数(a,b,... args)args包含arguments.length的参数3
Pet*_*eng 13
如前所述,您可以使用该arguments对象来检索可变数量的函数参数.
如果要使用相同的参数调用另一个函数,请使用apply.您甚至可以通过转换arguments为数组来添加或删除参数.例如,此函数在登录到控制台之前插入一些文本:
log() {
let args = Array.prototype.slice.call(arguments);
args = ['MyObjectName', this.id_].concat(args);
console.log.apply(console, args);
}
Run Code Online (Sandbox Code Playgroud)
虽然我普遍认为命名参数方法是有用且灵活的(除非你关心顺序,在这种情况下参数最简单),但我确实担心mbeasley方法的成本(使用默认值和扩展).这是拉动默认值所需的极高成本.首先,默认值在函数内定义,因此它们在每次调用时都会重新填充.其次,您可以使用||轻松读出命名值并同时设置默认值.无需创建和合并另一个新对象即可获取此信息.
function load(context) {
var parameter1 = context.parameter1 || defaultValue1,
parameter2 = context.parameter2 || defaultValue2;
// do stuff
}
Run Code Online (Sandbox Code Playgroud)
这大致相同的代码量(可能略多),但应该是运行时成本的一小部分.
虽然@roufamatic确实显示了arguments关键字的使用,而@Ken显示了一个使用对象的一个很好的例子,但我觉得它并没有真正解决这个实例中发生的事情,可能会混淆未来的读者或灌输一个不好的做法,因为没有明确说明一个函数/ method旨在获取可变数量的参数/参数.
function varyArg () {
return arguments[0] + arguments[1];
}
Run Code Online (Sandbox Code Playgroud)
当另一个开发人员查看您的代码时,很容易假设此函数不接受参数.特别是如果该开发人员不知道arguments关键字.因此,遵循风格指南并保持一致是个好主意.我将使用Google的所有示例.
让我们明确说明同一个函数有变量参数:
function varyArg (var_args) {
return arguments[0] + arguments[1];
}
Run Code Online (Sandbox Code Playgroud)
有时可能需要一个对象,因为它是数据映射中唯一经过批准和考虑的最佳实践方法.关联数组不受欢迎并且不鼓励.
SIDENOTE: arguments关键字实际上使用数字作为键返回一个对象.原型继承也是对象家族.请参阅答案的结尾以了解JS中正确的数组使用情况
在这种情况下,我们也可以明确说明这一点.注意:此命名约定不是由Google提供的,而是显式声明param类型的示例.如果您希望在代码中创建更严格的类型模式,这一点很重要.
function varyArg (args_obj) {
return args_obj.name+" "+args_obj.weight;
}
varyArg({name: "Brian", weight: 150});
Run Code Online (Sandbox Code Playgroud)
这取决于您的功能和程序的需求.例如,如果你只想在迭代过程中返回所有传递的参数的值,那么肯定会坚持使用arguments关键字.如果您需要定义参数和数据映射,那么对象方法就是您的选择.让我们看看两个例子,然后我们就完成了!
function sumOfAll (var_args) {
return arguments.reduce(function(a, b) {
return a + b;
}, 0);
}
sumOfAll(1,2,3); // returns 6
Run Code Online (Sandbox Code Playgroud)
function myObjArgs(args_obj) {
// MAKE SURE ARGUMENT IS AN OBJECT OR ELSE RETURN
if (typeof args_obj !== "object") {
return "Arguments passed must be in object form!";
}
return "Hello "+args_obj.name+" I see you're "+args_obj.age+" years old.";
}
myObjArgs({name: "Brian", age: 31}); // returns 'Hello Brian I see you're 31 years old
Run Code Online (Sandbox Code Playgroud)
如上所述,arguments关键字实际上返回一个对象.因此,必须调用要用于数组的任何方法.一个例子:
Array.prototype.map.call(arguments, function (val, idx, arr) {});
Run Code Online (Sandbox Code Playgroud)
要避免这种情况,请使用rest参数:
function varyArgArr (...var_args) {
return var_args.sort();
}
varyArgArr(5,1,3); // returns 1, 3, 5
Run Code Online (Sandbox Code Playgroud)
小智 6
请注意,按照 Ken 的建议传递具有命名属性的对象会增加为每次调用分配和释放临时对象的成本。通过值或引用传递普通参数通常是最有效的。对于许多应用程序来说,性能并不重要,但对于某些应用程序来说,性能可能很重要。
| 归档时间: |
|
| 查看次数: |
313084 次 |
| 最近记录: |