我想比较两个数组。。。理想地、有效地。没有什么稀奇古怪的,如果它们是相同的,那就是真的,如果不是,那就是假的。毫不奇怪,比较运算符似乎不起作用。

var a1 = [1,2,3];
var a2 = [1,2,3];
console.log(a1==a2);    // Returns false
console.log(JSON.stringify(a1)==JSON.stringify(a2));    // Returns true

JSON对每个数组进行编码,但是否有一种更快或“更好”的方法来简单地比较数组而不必遍历每个值?


当前回答

这里有一个CoffeeScript版本,适合那些喜欢它的人:

Array.prototype.equals = (array) ->
  return false if not array # if the other array is a falsy value, return
  return false if @length isnt array.length # compare lengths - can save a lot of time

  for item, index in @
    if item instanceof Array and array[index] instanceof Array # Check if we have nested arrays
      if not item.equals(array[index]) # recurse into the nested arrays
        return false
    else if this[index] != array[index]
      return false # Warning - two different object instances will never be equal: {x:20} != {x:20}
  true

所有学分都归@tomas zato所有。

其他回答

以下是我的解决方案:

/**
 * Tests two data structures for equality
 * @param {object} x
 * @param {object} y
 * @returns {boolean}
 */
var equal = function(x, y) {
    if (typeof x !== typeof y) return false;
    if (x instanceof Array && y instanceof Array && x.length !== y.length) return false;
    if (typeof x === 'object') {
        for (var p in x) if (x.hasOwnProperty(p)) {
            if (typeof x[p] === 'function' && typeof y[p] === 'function') continue;
            if (x[p] instanceof Array && y[p] instanceof Array && x[p].length !== y[p].length) return false;
            if (typeof x[p] !== typeof y[p]) return false;
            if (typeof x[p] === 'object' && typeof y[p] === 'object') { if (!equal(x[p], y[p])) return false; } else
            if (x[p] !== y[p]) return false;
        }
    } else return x === y;
    return true;
};

适用于任何嵌套的数据结构,显然忽略了对象的方法。甚至不要考虑用这个方法扩展Object.prototype,当我尝试过一次时,jQuery坏了;)

对于大多数阵列,它仍然比大多数串行化解决方案更快。这可能是对象记录数组最快的比较方法。

我喜欢将Undercore库用于数组/对象密集型编码项目。。。在Undercore和Lodash中,无论您是比较数组还是对象,它看起来都是这样的:

_.isEqual(array1, array2)   // returns a boolean
_.isEqual(object1, object2) // returns a boolean

Undercore is Equal文档Lodash isEqual文档

此函数比较两个任意形状和尺寸的数组:

function equals(a1, a2) {

    if (!Array.isArray(a1) || !Array.isArray(a2)) {
        throw new Error("Arguments to function equals(a1, a2) must be arrays.");
    }

    if (a1.length !== a2.length) {
        return false;
    }

    for (var i=0; i<a1.length; i++) {
        if (Array.isArray(a1[i]) && Array.isArray(a2[i])) {
            if (equals(a1[i], a2[i])) {
                continue;
            } else {
                return false;
            }
        } else {
            if (a1[i] !== a2[i]) {
                return false;
            }
        }
    }

    return true;
}

当两个数组具有相同的元素但顺序不同时,代码将无法正确处理这种情况。

看看我的代码,看看你的示例,它比较了两个元素为数字的数组,你可以修改或扩展它以用于其他元素类型(通过使用.jjoin()而不是.toString())。

变量a1=[1,2,3];变量a2=[1,2,3];const arrayAreEqual=a1.sort().toString()==a2.sort(().toString();//如果两个数组具有相同的元素,则为true,否则为falseconsole.log(arrayAreEqual);

使用数字/字符串/数组/对象的Ré草书cmp函数

<脚本>var cmp=函数(元素,目标){if(元素类型!==目标类型){return false;}否则if(typeof element==“object”&&(!target||!element)){返回目标==元素;}else if(元素类型==“对象”){var keys_element=对象.keys(元素);var keys_target=对象.keys(目标);如果(keys_element.length!==keys_target.length){return false;}其他的{对于(var i=0;i<keys_element.length;i++){如果(keys_element[i]!==keys_target[i])return false;if(!cmp(元素[keys_element[i]],目标[keys_target[i]]))return false;}返回true;}}其他的{返回元素==目标;}};console.log(cmp({键1:3,key2:“字符串”,key3:[4,“45”,{key4:[5,“6”,false,null,{v:1}]}]}, {键1:3,key2:“字符串”,key3:[4,“45”,{key4:[5,“6”,false,null,{v:1}]}]})); // 真的console.log(cmp({键1:3,key2:“字符串”,key3:[4,“45”,{key4:[5,“6”,false,null,{v:1}]}]}, {键1:3,key2:“字符串”,键3:[4,“45”,{键4:[5,“6”,未定义,null,{v:1}]}]})); // 假的</script>