js实现一个深比较 isEquals

前沿

在前端我们比较两个值是否相等一般都是使用==,===,如有在比较对象的时候,会遍历这个对象的key,然后拿到key所对应的value,然后去比较两个对象key所对应的value是否相等。 数组也是同样道理,遍历比较就可了。

  • 例如:
javascript 复制代码
const obj = {key:1, value:1}
const obj1 = {key:1, value:1}

obj === obj1  // fasle
isEqual(obj, obj1)  // true,因为虽然对象的引用地址不同,但是对象key所对应的value是相同的。

const isEquals = (obj, otherObj) => {
    for(let key in obj){
        if(key in otherObj){
            return obj[key] === otherObj[key]
        } else {
            return false
        }
    }
    
    for(let key in otherObj){
        if(key in obj){
            return obj[key] === otherObj[key]
        }else {
            return false
        }
    }
    return true
}

上面我们实现了一个简单的isEquals方法,我们只对对象的一层进行比较。如果让我们实现一个对象深层次的比较,该如实现呢?

实现

有这样两个深层次的对象,如下:

css 复制代码
const obj1 = {
    key:1,
    name:"jack",
    value: { name: 'jack', value: 1},
    arr: [1, 2, 3],
    innerArr: [1,2, { name: 'tom', value: 1 }]
}

const obj2 = {
    key:1,
    name:"jack",
    value: { name: 'jack', value: 1},
    arr: [1, 2, 3],
    innerArr: [1,2, { name: 'tom', value: 1 }]
}

const obj3 = {
    key:1,
    name:"jack",
    value: { name: 'jack', value: 2},
    arr: [1, 2, 3],
    innerArr: [1,2, { name: 'tom', value: 3 }]
}
  • 上面三个对象,obj1obj2是相同的,obj1obj3valueinnerArr[2].value是不同的
  • 所以isEquals(obj1, obj2) === true,isEquals(obj1, obj3) === false

实现

我们还是沿用上面写的isEquals,只不过在比较的时候,如果发现两个不相等,那么我们只需要递归调用就可以了,然后在添加下处理基本数据类型的条件就可以啦。实现如下:

vbnet 复制代码
const isEqusls = (obj, otherObj) => {
  // 如果是 null 或 undefined,在这里判断
  if (obj == null || otherObj == null) {
    return obj === otherObj
  }
  // number boolean function string 在这里判断
  if (typeof obj !== 'object' || typeof otherObj !== 'object') {
    return obj === otherObj
  }
  
  // 如果是引用数据类型,那么遍历进行比较
  for (let key in obj) {
    if (!(key in otherObj)) {
      return false
    }
  }

  for (let key in otherObj) {
    if (!(key in otherObj)) {
      return false
    }
    const value = obj[key]
    const otherValue = otherObj[key]
    if (value !== otherValue) {
      // 如果递归的时候返回了 false , 那么我们 return false,
      // 如果返回时 true, 那么那么继续遍历比较
      let flag = isEqusl(value, otherValue)
      if(!flag) return false
    }
  }
  return true
}
相关推荐
谙忆10241 小时前
前端图片直传对象存储:OSS/S3 预签名 URL、STS 临时凭证与回调校验
前端
CHNE_TAO_EMSM2 小时前
Android studio 打开文件时自动下载源码
前端·javascript·android studio
一孤程3 小时前
Airtest自动化测试第五篇:小程序与Web测试——跨平台自动化全覆盖
前端·自动化测试·小程序·自动化·测试·airtest
IT_陈寒3 小时前
SpringBoot自动配置不是你以为的那样的智能
前端·人工智能·后端
yume_sibai4 小时前
大屏数据可视化 - 边框红绿呼吸灯实现详解
前端·信息可视化·typescript
竹林8184 小时前
从 ethers.js 迁移到 Viem:一个签名验证 Bug 让我彻底放弃旧爱
javascript
Hyyy4 小时前
很多Desktop都在上的Computer Use是什么
前端·llm
慢功夫4 小时前
开篇:VS Code 为什么不是一个普通 React App
前端·visual studio code
你挚爱的强哥5 小时前
Vue2 实现 1.5s 十连击监听(连续点击若干次),封装通用可复用点击检测工具,不用 data!Vue 封装通用连击监听方法,支持自定义时长与点击次数
前端·javascript·vue.js
半个落月5 小时前
用 LangChain.js 手写一个能读写文件和执行命令的 Mini Cursor
javascript·人工智能·后端