JS AWS GenAI LIVE 中的 const 📦、seal 🤐、freeze ❄️ 和 immutability 🤓!

2025-06-04

JS 中的 const 📦、seal 🤐、freeze ❄️ 和 immutability 🤓

AWS GenAI 直播!

不可变数据一旦创建就无法更改。大多数情况下,这会使代码更简洁,错误更少。这就是为什么不可变数据结构经常成为热门话题的原因。让我们看看用 JS 能实现什么!

你可能会说, const肯定赢了,因为这样你就能创建常量了,对吧?嗯……不对。使用 const,你创建的变量无法被重新赋值。

因此下面的代码将无法工作:

const x = "Dog"
x = "Cat" // crashes with "Uncaught TypeError: Assignment to constant variable."

当然,使用letvar可以重新分配变量。

那么,为什么 const 不是不可变的呢?让我们看看当我们使用对象而不是原始值时会发生什么。

const obj =  { name: "Doggo" }
// let's change a property
obj.name = "Kitty"
// and add one
obj.animal = "cat"

console.log(obj) // {name: "Kitty", animal: "cat"}

// reassigning will not work
obj = { name: "Birdo" } // crashes with "Uncaught TypeError: Assignment to constant variable."

因此,我们仍然可以添加和更改对象的属性。但是 Object 中有一个seal方法和一个freeze方法,它们的作用基本上与它们的名称完全一致。我们先来看看seal

const obj =  { name: "Doggo" }
// let's seal our object
Object.seal(obj)
// let's change the property again
obj.name = "Kitty"
// and also add one again
obj.animal = "cat"

console.log(obj) // {name: "Kitty"}

那么这里发生了什么?name属性可以更改,但animal属性却无法添加。这正是seal的作用:它阻止向对象添加属性。现有属性仍然可以更改。

冻结方法可以防止更改以及添加/删除属性。

const obj =  { name: "Doggo" }
// let's freeze our object
Object.freeze(obj)
// let's change the property again
obj.name = "Kitty"
// and also add one again
obj.animal = "cat"

console.log(obj) // {name: "Doggo"}

好吧,那么将const与Object.freeze结合使用就能实现不可变性,对吗?嗯……还是不行。freeze 方法并非所谓的深度冻结。这意味着,只有第一层对象真正被冻结;该对象内的其他对象不会被冻结。我们来看一个例子:

// we'll give the dog an owner, that also has a name (mine ;) 
const obj = { name: "Doggo", owner: { name: "Ben" } }
// we'll again freeze the object
Object.freeze(obj)

// and this time we'll change the name of the owner
obj.owner.name = "Bla"

console.log(obj) // {name: "Doggo", owner: {name: "Bla"}}

为了真正实现不可变性,你可以创建一个深度冻结方法,递归地运行所有对象属性并冻结所有嵌套对象。如果你对此教程感兴趣,请告诉我!

或者您可以使用像Immutable.js这样的库


想要提升 Web 开发能力?
🚀🚀🚀订阅我的每周✉️简报

文章来源:https://dev.to/benjaminmock/const-seal-freeze-immutability-in-js-2m77
PREV
你知道 📦 JS 中的自动装箱是什么吗?
NEXT
参数和参数——您知道它们的区别吗?