我想比较两个数组。。。理想地、有效地。没有什么稀奇古怪的,如果它们是相同的,那就是真的,如果不是,那就是假的。毫不奇怪,比较运算符似乎不起作用。
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对每个数组进行编码,但是否有一种更快或“更好”的方法来简单地比较数组而不必遍历每个值?
代码高尔夫
有很多答案表明如何有效地比较数组。
以下是比较两个int或(字符串)数组的最短方法,以代码字节为单位。
常量a=[1,2,3]常量b=[1,2,3]console.log(“1.”,a.join()==b.join(())console.log(“2.”,a.join()==[].join())console.log(“3.”,1+a==1+b)console.log(“4.”,1+[]==1+b)//甚至更短console.log(“4.b)”,a==“”+b)//误报(见缺陷)console.log(“5.”,1+[“3”]==1+[3])//类型差异console.log(“6.”,1+[“1,2”]==1+[“1”,“2”])
解释
这是因为当使用+运算符时,类型会自动转换为允许串联。在这种情况下,1和[1,2,3]都被转换为字符串。
在内部,JavaScript使用[1,2,3].join()将数组转换为字符串,然后将它们相加,得到11,2,3。在两个数组上执行此操作时,可以简单地使用==或==来比较两个字符串。
缺陷
使用此技术,比较不关心要比较的数组中的元素是否属于不同类型。由于字符串转换,[1,2]将等于[“1”,“2”]。
编辑:正如评论中指出的,比较字符串数组可能会产生误报,例如[“1,2”]等于[“1”,“2”]。如果您确信这些情况从未发生过(例如,在许多代码高尔夫挑战中),这一点就不重要了。
免责声明
虽然这对于代码高尔夫很有用,但可能不应该在生产代码中使用。指出的两个缺陷也无助于此。
我会这样做:
[2,3,4,5] == [2,3,4,5].toString()
当您使用“==”运算符时,javascript检查值(左侧和右侧)是否是相同的类型,如果是不同的,javascript尝试将两边转换为相同的类型。
Array == String
Array具有toString方法,因此javascript使用它将它们转换为相同的类型,工作方式如下:
[2,3,4,5].toString() == [2,3,4,5].toString()
如果数组是普通的,并且顺序很重要,那么这两行可能会有所帮助
//Assume
var a = ['a','b', 'c']; var b = ['a','e', 'c'];
if(a.length !== b.length) return false;
return !a.reduce(
function(prev,next,idx, arr){ return prev || next != b[idx] },false
);
Reduce遍历数组之一,如果“a”的至少一个元素与“b”的元素不相等,则返回“false”只需将其包装到函数中
令人惊讶的是,没有人提出解决办法
const a = [1, 2, 3]
const b = [1, 2, 3, 4]
a.find((v,i) => v !== b[i])
这里的好处是,它不会比较所有值,而是查找第一次出现的值,并尽早结束循环。换句话说,它不是问“两个数组相等吗?”而是问“一个数组与另一个数组不同吗?”。
绩效基准排名第三https://jsben.ch/TgFrA
记住,顺序很重要,a.find(…)!==b.find(…),可以通过a.length==b.length进行检查
if (a.length === b.length && a.find((v,i) => v !== b[i]) === undefined) {
// equal
}