【问题标题】:How to use string as a key to update object如何使用字符串作为更新对象的键
【发布时间】:2018-05-09 12:02:30
【问题描述】:

我正在尝试创建一个函数,该函数接受对象中的路径并将其作为键。

例如,如果我想更新城市,它是公司的子对象,它是属性的子对象,我可以这样做: originalObj['property']['company']['city'] = test

到目前为止,这是我的代码:

function updateObj(path, value){
  let valuePath = path.split(',')
  let key=''
  for(let i=0; i<valuePath.length ; i++){
    key = key+`[valuePath[${i}]]`
  }
   //key = [valuePath[0]] [valuePath[1]] [valuePath[2]]
  originalObj[key] = value
  }

setObj('property,company,city', test)

【问题讨论】:

  • 哦,有趣。这并不难,但它是 JavaScript 101 课程中一个很好的家庭作业练习。
  • 你有什么尝试...问题是什么?

标签: javascript


【解决方案1】:

您可以保存路径的最后一个键并使用临时对象来获取最终对象以分配值。

function updateObj(path, value) {
    var valuePath = path.split(','),
        last = valuePath.pop(),
        temp = object;

    for (let i = 0; i < valuePath.length; i++) {
        temp = temp[valuePath[i]];
    }
    temp[last] = value;
}

var object = { property: { company: { city: 'London' } } };

updateObj('property,company,city', 'New York');

console.log(object);

Array#reduce

function updateObj(path, value) {
    var valuePath = path.split(','),
        last = valuePath.pop();

    valuePath.reduce((o, k) => o[k] = o[k] || {}, object)[last] = value;
}

var object = {};

updateObj('property,company,city', 'New York');

console.log(object);

【讨论】:

    【解决方案2】:
    function updateObj(obj, path, value){
     path.split(",").slice(0,-1).reduce((obj, key) => obj[key] || (obj[key] = {}), obj)[path.split(",").pop()] = value;
    }
    

    【讨论】:

    • 这是一个令人惊叹的单行代码,绝不应该在任何代码中使用。
    • 冗余拆分
    • @intervalia 仍然比缓存它的声明或 IIFE 短
    • @derek 同样适用于一般问题,不是吗?
    • @JonasW。我可以从中看到一些合法的用途。
    【解决方案3】:

    试试这个:

    function setObj(originalObj, path, value){
      var parts = path.split(',');
      var lastKey = parts.pop();
      var obj = originalObj;
    
      parts.forEach(
        function(key) {
          key = key.trim();
          obj[key] = obj[key] || {};
          obj = obj[key];
        }
      );
    
      obj[lastKey] = value;
    }
    
      var originalObj = {};
      var test = "This is a test";
      setObj(originalObj, 'property,company,city', test)
    
      console.log(JSON.stringify(originalObj,0,2));
    

    它遍历您的列表并为除最后一个之外的所有对象创建子对象。然后它使用最后一个作为密钥来存储value

    此代码的优点是您无需假定原始 Object 变量名称。而且,如果您希望它是纯粹的并且不影响原始对象结构,那么您可以进行以下细微更改:

    function setObj(originalObj, path, value){
      var parts = path.split(',');
      var lastKey = parts.pop();
      var newObj = Object.assign({}, originalObj);
      var obj = newObj;
    
      parts.forEach(
        function(key) {
          obj[key] = Object.assign({}, obj[key] || {});
          obj = obj[key];
        }
      );
    
      obj[lastKey] = value;
      return newObj;
    }
    
      var originalObj = {animals: {dog:"bark",cat:"meow"},property:{company:{name:"Fred's Things"}}};
      var test = "This is a test";
      var result = setObj(originalObj, 'property,company,city', test)
    
    
      console.log(JSON.stringify(originalObj,0,2));
      console.log(JSON.stringify(result,0,2));
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-12-23
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-09-24
      相关资源
      最近更新 更多