什么是深度不变性?
What is deep immutability?
在阅读 Promises/A+ 规范时,我遇到了术语 'deep immutability'。文字说:
Here, “must not change” means immutable identity (i.e. ===), but does not imply deep immutability.
什么是深度不变性?
有人可以举例说明吗?
一旦 promise 被解决,任何再次解决它的尝试都将无效,这意味着已解决的值将始终与原始已解决的值严格相等。但是,这并不意味着该值不能更改,即 "does not imply deep immutability".
这可以用一个例子来证明:
var value = [1];
var p = Promise.resolve(value);
p.then(a => console.log(a)); // [1]
p.then(a => console.log(a === value)); // true
p.then(a => { a = [2]; console.log(a);}); // [2]
p.then(a => console.log(a)); // [1]
p.then(a => { a[0] = 2; console.log(a);}); // [2]
p.then(a => console.log(a)); // [2]
p.then(a => console.log(a === value)); // true
如您所见,从已解决的承诺返回的值始终保持相同的对象值 - a === value
。将对象绑定到不同值的尝试仅适用于 then 块的范围内,下次我们在 promise 上调用 then 方法时,我们会看到原始对象值。
当我们改变这个数组的一个属性的值时,在本例中是第一个元素,我们注意到这个改变会影响原始值,因此也会影响从这个承诺返回的解析值。如果已解析的值具有深度不变性,那么它的所有属性及其属性都将是不可变的,但是我们刚刚证明情况并非如此。
在面向对象语言中,没有锁定对象 属性 的好方法。例如,如果您的应用程序中有一个对象的多个实例化,并且您更改了其中一个引用的 属性 值,那么该对象的至少一个引用之间的数据现在会有所不同。 Deeply Immutable 确保该对象的数据在所有引用中按规范以编程方式保持锁定。
如果应用程序规范声明深度不变性,那么改变对象或重新分配其字段都是非法的。
如果应用程序声明浅层不变性,您仍然无法重新分配对象字段,因此是不可变的,但您可以改变对象引用。
这里有一篇很棒的文章 https://homes.cs.washington.edu/~mernst/pubs/immutability-aliasing-2013-lncs7850.pdf
根据这篇文章,大多数客户更喜欢深度不适应。
在阅读 Promises/A+ 规范时,我遇到了术语 'deep immutability'。文字说:
Here, “must not change” means immutable identity (i.e. ===), but does not imply deep immutability.
什么是深度不变性? 有人可以举例说明吗?
一旦 promise 被解决,任何再次解决它的尝试都将无效,这意味着已解决的值将始终与原始已解决的值严格相等。但是,这并不意味着该值不能更改,即 "does not imply deep immutability".
这可以用一个例子来证明:
var value = [1];
var p = Promise.resolve(value);
p.then(a => console.log(a)); // [1]
p.then(a => console.log(a === value)); // true
p.then(a => { a = [2]; console.log(a);}); // [2]
p.then(a => console.log(a)); // [1]
p.then(a => { a[0] = 2; console.log(a);}); // [2]
p.then(a => console.log(a)); // [2]
p.then(a => console.log(a === value)); // true
如您所见,从已解决的承诺返回的值始终保持相同的对象值 - a === value
。将对象绑定到不同值的尝试仅适用于 then 块的范围内,下次我们在 promise 上调用 then 方法时,我们会看到原始对象值。
当我们改变这个数组的一个属性的值时,在本例中是第一个元素,我们注意到这个改变会影响原始值,因此也会影响从这个承诺返回的解析值。如果已解析的值具有深度不变性,那么它的所有属性及其属性都将是不可变的,但是我们刚刚证明情况并非如此。
在面向对象语言中,没有锁定对象 属性 的好方法。例如,如果您的应用程序中有一个对象的多个实例化,并且您更改了其中一个引用的 属性 值,那么该对象的至少一个引用之间的数据现在会有所不同。 Deeply Immutable 确保该对象的数据在所有引用中按规范以编程方式保持锁定。
如果应用程序规范声明深度不变性,那么改变对象或重新分配其字段都是非法的。
如果应用程序声明浅层不变性,您仍然无法重新分配对象字段,因此是不可变的,但您可以改变对象引用。
这里有一篇很棒的文章 https://homes.cs.washington.edu/~mernst/pubs/immutability-aliasing-2013-lncs7850.pdf
根据这篇文章,大多数客户更喜欢深度不适应。