javascript数组推送问题

时间:2011-07-18 09:37:47

标签: javascript arrays push

我有以下javascript代码:

var objectArray = [];
var allInputObjects = [];
var allSelectObjects = [];
var allTextAreaObjects = [];

//following returns 3 objects
allInputObjects = document.getElementById("divPage0").getElementsByTagName("INPUT");

//following returns 1 object
allSelectObjects = document.getElementById("divPage1").getElementsByTagName("SELECT");

//following returns 0 objects
allTextAreaObjects = document.getElementById("divPage2").getElementsByTagName("TEXTAREA");

//and following statement does not work
objectArray = allInputObjects.concat(allSelectObjects);

我的问题是最后一行是抛出错误。

我在Firefox中尝试了上述代码,它说allInputObjects.concat不是函数。

任何线索,我相信脚本不会将allInputObjects视为数组!

任何帮助将不胜感激。

4 个答案:

答案 0 :(得分:4)

为什么您认为allSelectObjects 是一个数组?

它最初被分配给一个空数组,当然。但是它被第6行(ish)上的getElementsByTagName调用覆盖了。 Javascript中的变量不是强类型的,因此初始赋值不会强制以后的赋值也是数组。

我怀疑当你调用最后一行时,你会在变量中有某种类型的NodeList或类似的,而不是数组。 (这至少是Firefox中的returned by the method。)

答案 1 :(得分:4)

getElementsByTagName返回NodeList,类似于Array,但它不支持所有原型函数。

要将类似数组的对象无缝转换为数组,请使用:

var arr = Array.prototype.slice.call(somenodelist, 0);

arr几乎完全相同,只是它现在支持Array原型函数,例如concat

该函数实际上做的是返回包含Array元素的部分somenodelist,准确地说是索引0和之后的所有内容。显然,这只是所有元素,因此这是将类似数组的对象转换为真实Array的技巧。

答案 2 :(得分:3)

正如Andezej指出的那样,你在这里没有处理数组,你正在处理一种节点列表。

根据getElementsByTagName

的结果,您可以使用以下方法创建要使用的数组
        var tags = obj.getElementsByTagName('input');
        for (var j=0;j<tags.length;j++) {
            resultArray.push(tags[j]);
        }

答案 3 :(得分:1)

NodeList转换为数组的另一种有趣方式:

var tags = obj.getElementsByTagName('input'),
    tags2Arr = ( 
           function toArr(i){
             return i ? toArr(i-1).concat(tags[i]) : [tags[0]];
           }(tags.length-1) 
    );

现在,如果您向Array.prototype添加方法:

Array.prototype.clone = function() {
    var arr = this;
    return (function clone(i){
     return i ? clone(i-1).concat(arr[i]) : [arr[0]];
    })(this.length-1);
};

您可以使用此oneliner将NodeList转换为数组:

Array.prototype.clone.call(obj.getElementsByTagName('input'));