【问题标题】:Having problems with python遇到python问题
【发布时间】:2017-05-02 19:03:29
【问题描述】:

我有一些...

[{"countryname": "Republic of Tunisia", "project_name": "TN: DTF Social Protection Reforms Support", "lendprojectcost": 5700000}, 
{"countryname": "Republic of Tunisia", "project_name": "Tunisia: Ecotourism and Conservation of Desert Biodiversity", "lendprojectcost": 9050000},
{"countryname": "Republic of Tunisia", "project_name": "Tunisia - Communications for policy reforms", "lendprojectcost": 600000},
{"countryname": "Republic of Tunisia", "project_name": "Tunisia - Governance, Opportunities and Jobs DPL", "lendprojectcost": 500000000}]

我想要:

[{"countryname": "Republic of Tunisia", "project_name":all projects, "lendprojectcost":sum(..) }]

我该怎么做? 我使用了 Python/Flask/MongoDB。

【问题讨论】:

  • 请让你的代码看起来像python,带有变量名。我们都是老的、近视的、戴眼镜的人,解析原始 JSON 真的很痛苦。
  • 使用一些for 循环来完成。
  • 你希望你的all_projects:作为一个列表,作为一个字符串,等等?
  • @engineercoding 这只是成本的总和。 OP 想要总成本和项目列表。

标签: python json mongodb list


【解决方案1】:

您可以先创建一个dict 对象,通过使用collections.defaultdict 来制作每个"countryname" 的唯一条目。然后将dict 转换为您想要的响应。

例如:

from collections import defaultdict

country_project, country_sum = defaultdict(list), defaultdict(int)

for country in country_list:
    country_name = country["countryname"]
    country_project[country_name].append(country['project_name'])
    country_sum[country_name] += country['lendprojectcost']

# Map the `dict` to get desired result using list comprehension
new_list = [ {
        'countryname': country,
        'project_name': country_project[country],
        'lendprojectcost': country_sum[country]} for country in country_project]

# OR, via using plain `for` loop as:
# new_list = []
# for country in country_project:
#     new_list.append({
#         'countryname': country,
#         'project_name': country_project[country],
#         'lendprojectcost': country_sum[country]})

其中country_list 是问题中提到的原始列表,my_list 持有的最终值是期望的结果:

[{
    'countryname': 'Republic of Tunisia', 
    'project_name': [
        'TN: DTF Social Protection Reforms Support', 
        'Tunisia: Ecotourism and Conservation of Desert Biodiversity', 
        'Tunisia - Communications for policy reforms', 
        'Tunisia - Governance, Opportunities and Jobs DPL'
    ], 
    'lendprojectcost': 515350000
}] 

【讨论】:

  • 怎么样new_list = [{'countryname': country, 'project_name': country_project[country], 'lendprojectcost': country_sum[country]} for country in country_project]。列表推导规则。
  • @DYZ:我认为这对用户来说可能太复杂了。但是在看到您的评论并重新考虑之后,我想我也应该提到这一点。更新了答案
  • 等等,country_list 是什么?
  • 答案中提到了“where country_list 是问题中提到的原始列表”
  • @R.B 还要检查我发布的基于熊猫的 5 行答案。它不需要国家列表的知识。
【解决方案2】:

作为一个 pandas 极客,我会选择一个 pandas 解决方案:从原始数据创建一个数据框(我们称之为 raw),进行所有必要的聚合,然后构建另一个字典:

df = pd.DataFrame(raw)
result_df = df.groupby('countryname').agg({
                       'lendprojectcost' : np.sum,
                       'project_name'    : lambda col: col.tolist()})
result = result_df.reset_index().to_dict(orient="records")

# [{"countryname":"Republic of Tunisia","project_name":["TN: DTF Social Protection Reforms Support","Tunisia: Ecotourism and Conservation of Desert Biodiversity","Tunisia - Communications for policy reforms","Tunisia - Governance, Opportunities and Jobs DPL"],"lendprojectcost":515350000}]

【讨论】:

    【解决方案3】:

    这里的其他答案很好,但这对于reduce 来说似乎是一个自然问题。您有一个列表,并且您正在尝试将列表中的元素与操作结合起来,以便将列表大小“减少”到一个元素:

    def update(x, y):
        x["project_name"].append(y["project_name"])
        x["lendprojectcost"] += y["lendprojectcost"]
        return x
    
    result = [reduce(update, list_of_dicts, {"countryname": "Republic of Tunisia",
                                             "project_name": [],
                                             "lendprojectcost": 0})]
    

    额外功能:无需导入

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-05-26
      • 2020-08-06
      • 2014-12-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多