2691. 不可变辅助工具 🔒
题目描述
创建带有微小修改的不可变对象的克隆副本是一个繁琐的过程。请你编写一个名为 ImmutableHelper 的类,作为满足这一要求的工具。构造函数接受一个不可变对象 obj ,该对象将是一个 JSON 对象或数组。
该类有一个名为 produce 的方法,它接受一个名为 mutator 的函数。该函数返回一个新的对象,它与原始对象相似,但应用了这些变化。
mutator 函数接受 obj 的 代理 版本。函数的使用者可以(看起来)对该对象进行修改,但原始对象 obj 实际上没有被改变。
例如,用户可以编写如下代码:
const originalObj = {"x": 5};
const helper = new ImmutableHelper(originalObj);
const newObj = helper.produce((proxy) => {
  proxy.x = proxy.x + 1;
});
console.log(originalObj); // {"x": 5}
console.log(newObj); // {"x": 6}
mutator 函数的属性:
- 它始终返回 
undefined。 - 它永远不会访问不存在的键。
 - 它永远不会删除键( 
delete obj.key)。 - 它永远不会在代理对象上调用方法( 
push、shift等)。 - 它永远不会将键设置为对象( 
proxy.x = {})。 
关于如何测试解决方案的说明:解决方案验证器仅分析返回结果与原始 obj 之间的差异。进行完全比较的计算开销太大。此外,对原始对象进行的任何变更都将导致答案错误。
示例 1:
输入:
obj = {"val": 10}, 
mutators = [
  proxy => { proxy.val += 1; },
  proxy => { proxy.val -= 1; }
]
输出:
[
  {"val": 11},
  {"val": 9}
]
解释:
const helper = new ImmutableHelper({val: 10});
helper.produce(proxy => { proxy.val += 1; }); // { "val": 11 }
helper.produce(proxy => { proxy.val -= 1; }); // { "val": 9 }
示例 2:
输入:
obj = {"arr": [1, 2, 3]} 
mutators = [
 proxy => { 
   proxy.arr[0] = 5; 
   proxy.newVal = proxy.arr[0] + proxy.arr[1];
 }
]
输出:
[
  {"arr": [5, 2, 3], "newVal": 7 } 
]
解释:对原始数组进行了两次编辑。首先将数组的第一个元素设置为 5。然后添加了一个值为 7 的新键。
示例 3:
输入:
obj = {"obj": {"val": {"x": 10, "y": 20}}}
mutators = [
  proxy => { 
    let data = proxy.obj.val; 
    let temp = data.x; 
    data.x = data.y; 
    data.y = temp; 
  }
]
输出:
[
  {"obj": {"val": {"x": 20, "y": 10}}}
]
解释:交换了 "x" 和 "y" 的值。
提示:
2 <= JSON.stringify(obj).length <= 4 * 105produce() 的总调用次数 < 105
解法
方法一
1 |  |