如何使用ES7的Set或Map方法比较JavaScript对象是否相等
直接解答:如何判断两个Set的取值是否完全一致
JS原生的Set没有内置的相等判断方法,直接用===比较只会对比对象引用,永远不会返回两个不同Set实例相等。可以通过固定的两步逻辑判断两个Set元素完全一致:
- 第一步:先对比两个Set的元素总数,只要大小不相等直接判定不相等
- 第二步:遍历其中一个Set的所有元素,逐元素检查另一个Set是否存在对应值,只要有一个元素缺失就判定不相等
对应的实现代码:
function isSetEqual(setA, setB) { if (setA.size !== setB.size) return false; for (const item of setA) { if (!setB.has(item)) return false; } return true; } // 调用你之前生成的两个Set做对比 const newSet1 = new Set(Object.values(object1)); const newSet2 = new Set(Object.values(object2)); console.log(isSetEqual(newSet1, newSet2));
重要提醒:仅对比值集合的方案无法实现正确的对象相等校验
你当前把值存进Set再对比的思路存在两个无法规避的硬伤,根本不能准确判断两个原对象的键值对是否相等:
- Set会自动去重,丢失原对象的值出现次数:比如对象A有两个键的值都是0,Set会合并成单个0元素;如果对象B有三个键的值都是0,去重后的Set和对象A的Set完全一致,但实际两个对象的键数量根本不匹配,显然不是相等的对象。
- 完全丢失了键和值的绑定关系:比如
{name: "张三", age: 18}和{name: 18, age: "张三"}两个对象,提取出来的值存进Set后完全一样,但键和值的对应关系完全错误,根本不是等价对象。
另外你示例里的object2存在语法错误,radio2: "none"行尾漏了逗号,会导致JS解析失败。
基于Set/Map的正确对象相等实现
要实现无键顺序依赖的对象键值对相等校验,必须同时检查两个核心维度:键集合完全一致、对应键的值完全相等,不能只对比值。针对你示例里全基础类型值的场景,可以用如下实现:
// 复用前面写好的Set判断函数 function isSetEqual(setA, setB) { if (setA.size !== setB.size) return false; for (const item of setA) { if (!setB.has(item)) return false; } return true; } function isObjectKeyEqual(objA, objB) { // 1. 先对比两个对象的键集合是否完全一致 const keySetA = new Set(Object.keys(objA)); const keySetB = new Set(Object.keys(objB)); if (!isSetEqual(keySetA, keySetB)) return false; // 2. 逐键对比对应的值是否相等 for (const key of keySetA) { if (objA[key] !== objB[key]) return false; } return true; } // 测试调用 console.log(isObjectKeyEqual(object1, object2));
这个方案的优势:
- 完全不依赖对象键的排列顺序,不会出现键顺序不同就判断不相等的问题
- 基于Set的哈希查找实现,时间复杂度为O(n),比JSON.stringify的序列化逐字符比对效率更高
- 能准确识别键缺失、多键、键值不匹配的场景
内容的提问来源于stack exchange,提问作者GoonGamja
相关产品推荐
相关产品推荐

