【问题标题】:merge complex list of nested dicts合并嵌套字典的复杂列表
【发布时间】:2019-08-18 16:35:45
【问题描述】:

我正在尝试根据“名称”将嵌套字典合并到一个列表中,如下所示:

[
  {
    "name": "abc",
    "metadata": [
        {
            "name": "foo",
            "data": [
                {
                    "version": "1.0"
                }
            ]
        },
        {
            "name": "foo",
            "data": [
                {
                    "version": "2.0"
                }
            ]
        },
        {
            "name": "bar",
            "data": [
                {
                    "version": "1.0"
                }
            ]
        }
    ]
},
{
    "name": "xyz",
    "metadata": [
        {
            "name": "bob",
            "data": [
                {
                    "version": "3.2"
                }
            ]
        },
        {
            "name": "alice",
            "data": [
                {
                    "version": "2.2"
                }
            ]
        }
    ]
},
{
    "name": "xyz",
    "metadata": [
        {
            "name": "mike",
            "data": [
                {
                    "version": "3.2"
                }
            ]
        },
        {
            "name": "alice",
            "data": [
                {
                    "version": "2.2"
                }
            ]
        }
      ]
  }
]

考虑到合并的项目在元数据中不应有重复项,我该如何在 Python 中做到这一点?元数据条目应该是唯一的,如果元数据中存在名称+数据+版本,则不应合并该条目。

我想要的输出应该是这样的

[
  {
    "name": "abc",
    "metadata": [
        {
            "name": "foo",
            "data": [
                {
                    "version": "1.0"
                }
            ]
        },
        {
            "name": "foo",
            "data": [
                {
                    "version": "2.0"
                }
            ]
        },
        {
            "name": "bar",
            "data": [
                {
                    "version": "1.0"
                }
            ]
        }
    ]
},
{
    "name": "xyz",
    "metadata": [
        {
            "name": "bob",
            "data": [
                {
                    "version": "3.2"
                }
            ]
        },
        {
            "name": "mike",
            "data": [
                {
                    "version": "3.2"
                }
            ]
        },
        {
            "name": "alice",
            "data": [
                {
                    "version": "2.2"
                }
            ]
        }
    ]
   }
]

【问题讨论】:

  • 你想要的输出是什么?
  • 我更新了帖子以包含我想要的输出
  • 如果第二个 "name":"xyz" 包含 {"name":"alice","data":[{"version":"8.8"}]} 作为其最后一个元数据元素会发生什么?
  • 好问题,它应该保留两者,因为它们的版本不同。所以它将继续同时拥有[{"name":"alice","data":[{"version":"2.2"}]},{"name":"alice","data":[{"version":"8.8"}]}]
  • @Ajax1234 你能解决这个问题吗?

标签: python arrays ordereddictionary


【解决方案1】:

你可以使用itertools.groubpy:

import itertools
d = [{'name': 'abc', 'metadata': [{'name': 'foo', 'data': [{'version': '1.0'}]}, {'name': 'foo', 'data': [{'version': '2.0'}]}, {'name': 'bar', 'data': [{'version': '1.0'}]}]}, {'name': 'xyz', 'metadata': [{'name': 'bob', 'data': [{'version': '3.2'}]}, {'name': 'alice', 'data': [{'version': '2.2'}]}]}, {'name': 'xyz', 'metadata': [{'name': 'mike', 'data': [{'version': '3.2'}]}, {'name': 'alice', 'data': [{'version': '2.2'}]}]}]
new_d = [[a, list(b)] for a, b in itertools.groupby(sorted(d, key=lambda x:x['name']), key=lambda x:x['name'])]
result = [{'name':a, 'metadata':[c for j in b for c in j['metadata']]} for a, b in new_d]
final_result = [{**i, 'metadata':[c for d, c in enumerate(i['metadata']) if all(a != c for a in i['metadata'][:d])]} for i in result]

import json
print(json.dumps(final_result, indent=4))

输出:

[
  {
    "name": "abc",
    "metadata": [
        {
            "name": "foo",
            "data": [
                {
                    "version": "1.0"
                }
            ]
        },
        {
            "name": "foo",
            "data": [
                {
                    "version": "2.0"
                }
            ]
        },
        {
            "name": "bar",
            "data": [
                {
                    "version": "1.0"
                }
            ]
        }
    ]
},
{
    "name": "xyz",
    "metadata": [
        {
            "name": "bob",
            "data": [
                {
                    "version": "3.2"
                }
            ]
        },
        {
            "name": "alice",
            "data": [
                {
                    "version": "2.2"
                }
            ]
        },
        {
            "name": "mike",
            "data": [
                {
                    "version": "3.2"
                }
            ]
         }
      ]
   }
]

【讨论】:

  • 非常感谢 Ajax1234,这就像一个魅力 :-)
猜你喜欢
  • 2018-03-25
  • 2019-08-31
  • 1970-01-01
  • 2021-02-12
  • 1970-01-01
  • 1970-01-01
  • 2021-11-25
相关资源
最近更新 更多