如何使用map()调用对象列表的常用方法
How to use map() to call method common to list of objects?
TL;DR:基本上,我试图使用Array.prototype.map()
调用上下文对象列表的通用方法。
假设我有这样的代码:
a.doSomething();
b.doSomething();
c.doSomething();
d.doSomething();
e.doSomething();
...
这太啰嗦了。我想把这段代码缩短成这样的
[a, b, c, d, e].map(doSomething);
因为我不想使用for
循环
我怎么能做到这一点与本地map
函数在JS中,没有任何外部库?
提前感谢!如果这篇文章太长,我很乐意编辑它。就冲我吼吧
相关问题:
如何使用map()调用对象列表上的类方法
如何为对象列表调用相同的方法?
我没有在相关问题中使用信息,因为Python和JS使用不同的范式,我不能保证它们会工作相同。如果我错了,请不要犹豫,把我烧死在火刑柱上。
额外信息,如果你想忽略:
我已经RTFM了,措辞和例子表明我不能用map
做上述操作。MDN文档将map
描述为"在数组中的每个元素上调用一个提供的函数",而MSDN文档说它"在数组的每个元素上调用一个函数,并返回一个数组"。我不是试图在数组上调用方法,我试图从几个上下文对象中调用方法。如果这是不可能的,是否有天然的填充物?
我在游戏中使用这种方法,所以速度是我的主要关注点。如果有一个更理想的方式来编码这个,请让我知道!
我能想到的最接近的
[a, b, c, d, e].forEach(function(item) {item.doSomething()});
使用[]。Map对于你的目的来说是没有意义的
编辑,你也可以这样做
Array.prototype.fnName = function(methodName) {
var args = Array.prototype.slice.call(arguments, 1);
this.forEach(function(item) {
item[methodName].apply(item, args);
});
};
我用的是fnName
,你也可以叫它fnMap
或者其他你觉得有意义的东西
你会像
那样使用它[a,b,c].fnName('doSomething', param1, param2 ...)
不假思索地回复。Array#map
目前在大多数浏览器中都得到支持,并且是ES5的一部分。查看MDN链接:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/map
[1,2,3,4,5].map(function(item){ console.log(item)}
将打印:
1
2
3
4
5
并返回undefined。如果返回如下内容:
[1,2,3,4,5].map(function(item){return 2*item})
它将返回:
[2,4,6,8,10]
但是不需要返回任何东西。您可以简单地执行forEach操作。
items.forEach(function(item){items.method()}
都是O(n)时间,因为对数组中的n个元素应用任何东西,至少需要n时间。For循环再好不过了
错<罢工>ES6支持#map
,但不是在所有浏览器/Node.js上都可用,除非设置不同的设置。罢工>
Underscorejs具有此功能,如果您确实需要外部库。查看他们的地图文档:http://underscorejs.org/#map
我在服务器代码中使用它,没问题。这应该适用于你的游戏。如果页面加载时间是一个问题,您总是可以自己扩展Array
的原型。
Array.map()
为数组中的每个项调用给定的函数。这就是使用匿名函数非常合适的地方:
[a, b, c].map(function (item) { item.doSomething(); });
看到这篇文章很老了,我想给出一些可能补充其他答案的元素。
让我们以一个简单的类A
为例,它有一个方法double
。
class A {
constructor(n) { this.n = n; }
double() { return 2 * this.n; }
}
我们将有一个实例数组来处理。
const data = [ new A(3), new A(12), new A(4), new A(10) ];
函数包装器
Array#map()
方法接受一个回调函数,它将对该数组的每个元素执行这个回调函数。
本质上归结为在对象上包装方法调用。为此,我们可以使用标准函数:
data.map(function(o) { return o.double() });
通常你会遇到一个箭头函数:
data.map(o => o.double());
,它减少了对括号、花括号和return
语句的需要。
Destructuring
现在我们可以试着改善这一点。实际上,我们可以在函数头文件中解构对象。下面,我们直接从对象中检索double并调用它:
data.map(({ double }) => double());
然而,这是行不通的…
TypeError:
this
isundefined
发生的是,我们没有在当前对象上调用double
。这是因为函数绑定,当作为函数独立调用double
时,我们没有设置this
的值。
可以将函数绑定到对象
data.map((o, _, __, fn=o.double) => fn.bind(o)())
但是…这将违背追求更短版本的目的。
类成员箭头函数!
但是,可以通过使用类成员箭头函数来解决这个问题。class A {
constructor(n) { this.n = n; }
double = () => { return 2 * this.n; }
}
这样在调用方法时就不需要绑定了。
那么我们就可以成功地做到:
data.map(({ double } => double());
请记住,这不是所有浏览器都支持的。而且为了使用这种语法,你必须修改你的类声明。我不太推荐它。类成员箭头函数对于事件处理程序来说非常好…
演示:
class A {
constructor(n) { this.n = n; }
double() { return 2 * this.n; }
triple = () => { return 3 * this.n; }
}
const data = [new A(3), new A(12), new A(4), new A(10)];
console.log(data.map(o => o.double()));
// console.log(data.map(({ double }) => double())); // won't work!
console.log(data.map((o, _,__, fn=o.double) => fn.bind(o)())); // ugly
console.log(data.map(({triple}) => triple()));
- 要求输入在数据列表中
- 从javascript创建一个列表
- 如何使用jQuery选择下拉列表的值
- 将输入字段中的文本提交到我的数据库,同时将其添加到我的列表中
- 将jsp文件下拉列表中的选定项分配给一个java变量(比如String selection)
- Javascript按钮下拉列表
- 如何使用json将对象列表从java转换为javascript
- 区分JSON中的矩阵和列表列表
- jQuery表单添加不适用于下拉列表
- 用每小时的差值填充数组/列表-从下拉列表中给定两个时间值
- 接受不在列表中的值-引导组合框
- 禁用jQuery中的下拉列表
- 从HTTPGET返回一个自定义对象列表,以便在Angular 2应用程序中使用
- 如何在javascript中迭代数字列表
- 如何在按钮中显示下拉列表中选定的元素
- 为什么HTML5拖放的目标是孩子?(可排序列表)
- 鼠标悬停事件影响列表中所有行中的按钮,而不仅仅是特定按钮
- 使用图像数组列表的simplegallary.js显示适合桌面屏幕的图像
- 如何在从多选下拉列表中选择选项值时动态生成文本框
- 如何使用map()调用对象列表的常用方法