简单比较两个结构未知的对象的方法

huangapple go评论61阅读模式
英文:

Simple way to compare two objects with unknown stuctures

问题

以下是翻译的代码部分:

让我们假设我有一个描述期望结果的对象:

{
    "property1" : "value1",
    "property2" : "value2",
    "property3" :{
        "property4" : "value4"
    }
}

我不关心所有额外的属性。例如,在这种情况下,我获得了实际结果如下,它将匹配,因为所有期望的属性都存在并具有期望的值:

{
   "property1":"value1",
   "property2":"value2",
   "property3":{
      "property4":"value4",
      "property5":"value5"
   },
   "property6":"value6"
}
这将不匹配:

{
   "property2":"value20",
   "property3":{
      "property4":"value4"
   }
}

这里的困难部分是我事先不知道结构;我需要一个可以匹配任何对象的函数。

到目前为止,我最好的想法是使用[lodash merge][1]来展平两个对象,使它们看起来像这样:

{
   "property1":"value1",
   "property2":"value2",
   "property3.property4":"value4",
   "property3.property5":"value5",
   "property6":"value6"
}

之后,我只需循环遍历所有期望的属性。尽管这个解决方案感觉很笨拙;是否有更简单、更容易实现的方法呢?

[1]: https://lodash.com/docs/4.17.15#mergeWith
英文:

Let's say I have object which describes expected result:

{
"property1" : "value1",
"property2" : "value2",
    "property3" :{
        "property4" : "value4"
    }
}

I don't care about all the extra properties. For example,in this case, I get actual result like this, and it will be a match, as all expected properties are present and have expected values:

{
   "property1":"value1",
   "property2":"value2",
   "property3":{
      "property4":"value4",
      "property5":"value5"
   },
   "property6":"value6"
}

And this will not be a match:

{
   "property2":"value20",
   "property3":{
      "property4":"value4"
   }
}

Difficult part here is that I don't know structure in advance; I need a function that would match any objects.

My best idea so far is to use lodash merge to flatten both objects so they look like this:

{
       "property1":"value1",
       "property2":"value2",
       "property3.property4":"value4",
       "property3.property5":"value5",
       "property6":"value6"
}

After which I can just cycle on all expected properties. This solution feels awkward, though; is there a simpler, easier way to accomplish this?

答案1

得分: 0

迭代地遍历对象的属性,并检查是否有属性本身是对象。如果找到对象,函数将以嵌套对象作为输入调用自身,然后遍历其属性。

function flattenObject(obj, parentKey = "") {
  let flattened = {};

  for (let key in obj) {
    if (obj.hasOwnProperty(key)) {
      let newKey = parentKey ? parentKey + "." + key : key;

      if (typeof obj[key] === "object") {
        let nestedObj = flattenObject(obj[key], newKey);
        flattened = { ...flattened, ...nestedObj };
      } else {
        flattened[newKey] = obj[key];
      }
    }
  }

  return flattened;
}

const myObj = {
  "property1": "value1",
  "property2": "value2",
  "property3": {
    "property4": "value4",
    "property5": "value5"
  },
  "property6": "value6"
};

const flattenedObj = flattenObject(myObj);
console.log(flattenedObj);

希望这对你有帮助。

英文:

Iterate recursively over the object's properties and checking if any of the properties are themselves objects. If an object is found, the function will call itself with the nested object as input and then iterate over its properties.

<!-- begin snippet: js hide: false console: true babel: false -->

<!-- language: lang-js -->

function flattenObject(obj, parentKey = &quot;&quot;) {
  let flattened = {};

  for (let key in obj) {
    if (obj.hasOwnProperty(key)) {
      let newKey = parentKey ? parentKey + &quot;.&quot; + key : key;

      if (typeof obj[key] === &quot;object&quot;) {
        let nestedObj = flattenObject(obj[key], newKey);
        flattened = { ...flattened,
          ...nestedObj
        };
      } else {
        flattened[newKey] = obj[key];
      }
    }
  }

  return flattened;
}
const myObj = {
  &quot;property1&quot;: &quot;value1&quot;,
  &quot;property2&quot;: &quot;value2&quot;,
  &quot;property3&quot;: {
    &quot;property4&quot;: &quot;value4&quot;,
    &quot;property5&quot;: &quot;value5&quot;
  },
  &quot;property6&quot;: &quot;value6&quot;
};

const flattenedObj = flattenObject(myObj);
console.log(flattenedObj);

<!-- end snippet -->

答案2

得分: 0

使用Lodashtransform函数以简单的方式遍历输入对象中的每个键值对,并使用isObject检查值是否是对象。如果值是对象,则实现会再次使用transform创建一个嵌套对象,使用点表示法将键与嵌套键连接起来。然后,使用assign将嵌套对象与结果对象合并:

const _ = require('lodash');
const flattenedObj = _.transform(myObj, function (result, value, key) {
  if (_.isObject(value)) {
    const nestedObj = _.transform(value, function (nestedResult, nestedValue, nestedKey) {
      nestedResult[key + '.' + nestedKey] = nestedValue;
    });
    _.assign(result, nestedObj);
  } else {
    result[key] = value;
  }
});
英文:

Simple way using Lodash's by transform function to iterate over each key-value pair in the input object, and checks if the value is an object using isObject. If the value is an object, the implementation creates a nested object using transform again, with a function that concatenates the key with the nested key using dot notation. The nested object is then merged with the result object using assign:

const _ = require(&#39;lodash&#39;);
const flattenedObj = _.transform(myObj, function (result, value, key) {
  if (_.isObject(value)) {
    const nestedObj = _.transform(value, function (nestedResult, nestedValue, nestedKey) {
      nestedResult[key + &#39;.&#39; + nestedKey] = nestedValue;
    });
    _.assign(result, nestedObj);
  } else {
    result[key] = value;
  }
});

huangapple
  • 本文由 发表于 2023年3月4日 02:23:55
  • 转载请务必保留本文链接:https://go.coder-hub.com/75630626.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定