You need to enable JavaScript to run this app. JavaScript中不使用Object.freeze()可以实现对象冻结吗?
优惠活动
大模型
产品
解决方案
定价
更多

JavaScript中不使用Object.freeze()可以实现对象冻结吗?

不使用Object.freeze()冻结对象的实现方案

首先明确:该需求可以实现,常用的原生实现方案有2种,无需额外依赖:

方案1:修改属性描述符+禁止对象扩展

该方案效果和原生Object.freeze()完全一致,直接修改原对象的属性配置:

const obj = {
  a:'test',
  b:'Something'
}

// 遍历所有自有属性,设置为不可修改、不可重新配置
Object.keys(obj).forEach(key => {
  Object.defineProperty(obj, key, {
    writable: false, // 禁止修改属性值
    configurable: false // 禁止删除属性、修改属性描述符
  })
})

// 禁止对象新增属性、修改原型
Object.preventExtensions(obj)

修改后对obj的赋值、删除属性、新增属性操作都会静默失败(严格模式下会抛出错误),和原生冻结效果完全相同。

方案2:使用Proxy代理拦截修改操作

该方案不会修改原对象,仅通过代理实例限制操作,适合需要保留原对象可修改能力的场景:

const obj = {
  a:'test',
  b:'Something'
}

const frozenObj = new Proxy(obj, {
  // 拦截属性赋值
  set: () => {
    throw new Error('无法修改冻结对象的属性')
  },
  // 拦截属性删除
  deleteProperty: () => {
    throw new Error('无法删除冻结对象的属性')
  },
  // 拦截新增/重定义属性
  defineProperty: () => {
    throw new Error('无法为冻结对象新增/重定义属性')
  },
  // 拦截原型修改
  setPrototypeOf: () => {
    throw new Error('无法修改冻结对象的原型')
  }
})

所有修改操作都需要通过frozenObj触发才会被拦截,直接操作原obj不受影响。

注意事项

如果需要实现深冻结效果,两种方案都需要递归处理所有嵌套的子对象,否则深层属性依然可以被修改。

内容的提问来源于stack exchange,提问作者Aniket

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.08 14:12:01