如何在querySelectorAll返回的伪数组上使用forEach?

时间:2012-12-19 17:00:00

标签: javascript dom

使用普通javascript的好处是能够对forEach,{{1}返回的项目使用mapfilterdocument.querySelectorAll等等等。

这样可以减少对jQuery的依赖,并简化代码。现在,这就是我们如何以丑陋的方式做到这一点:

document.getElementsBy*

这是......详细。

任何方式都可以立即使用[].forEach.call( document.querySelectorAll(sel), function(el) { }); 和喜欢的元素返回?

4 个答案:

答案 0 :(得分:14)

如果您在Chrome上进行测试,那么天真的方法就是这样做:

NodeList.prototype.forEach = Array.prototype.forEach;

这很有效。在Webkit上。但它不适用于Firefox。因为FF返回HTMLCollection ......

我发现的最常见的浏览器方式:

NodeList.prototype.forEach = HTMLCollection.prototype.forEach = Array.prototype.forEach;

它不适用于IE8及更低版本,因为它们在向宿主对象原型添加属性时会窒息。

完整列表:

NodeList.prototype.forEach = HTMLCollection.prototype.forEach = Array.prototype.forEach;
NodeList.prototype.map = HTMLCollection.prototype.map = Array.prototype.map;
NodeList.prototype.filter = HTMLCollection.prototype.filter = Array.prototype.filter;
NodeList.prototype.reduce = HTMLCollection.prototype.reduce = Array.prototype.reduce;
NodeList.prototype.reduceRight = HTMLCollection.prototype.reduceRight = Array.prototype.reduceRight;
NodeList.prototype.every = HTMLCollection.prototype.every = Array.prototype.every;
NodeList.prototype.some = HTMLCollection.prototype.some = Array.prototype.some;

或者,为了取悦我们亲爱的Bergi(还因为它 更清洁):

['forEach', 'map', 'filter', 'reduce', 'reduceRight', 'every', 'some'].forEach(
    function(p) {
    NodeList.prototype[p] = HTMLCollection.prototype[p] = Array.prototype[p];
});

考虑到与完美技能的联系,它在那里几乎无关紧要。问题是DOM在扩展时在浏览器上的行为大多不一样。除了IE< = 8。

之外,所有浏览器中的修改都是合理的

答案 1 :(得分:6)

function forEach( a, fn ) {
    return [].forEach.call(a, fn);
};

forEach(document.querySelectorAll(sel), function(el) {
});

还有更多:

function map( a, fn ) {
    return [].map.call(a, fn);
};
function filter( a, fn ) {
    return [].filter.call(a, fn);
};
function reduce( a, fn ) {
    return [].reduce.call(a, fn);
};
function reduceRight( a, fn ) {
    return [].reduceRight.call(a, fn);
};
function every( a, fn ) {
    return [].every.call(a, fn);
};
function some( a, fn ) {
    return [].some.call(a, fn);
};

也许你需要

[].slice.call(a)

在某些情况下。

function forEach(a, fn) {
    return [].forEach.call([].slice.call(a), fn);
}

答案 2 :(得分:2)

如果您不想更改原型并希望所有阵列功能都能正常工作,那么将您的集合转换为数组可能会更容易:

Array.from(document.querySelectorAll('a'))

所有数组函数都可用,在发布新版本的JavaScript时无需更新代码:

Array.from(document.querySelectorAll('a')).forEach(a => console.log(a))

答案 3 :(得分:0)

forEach现在无需转换即可直接使用

https://developer.mozilla.org/en-US/docs/Web/API/NodeList