首页 > 解决方案 > Python从包含列表的嵌套json中删除空字典

问题描述

我有一个深层嵌套的 json 文件,如下所示:

dict = [
{
"date":"2017-05-31",
"sections":[
 {
    "item":"BalanceSheetFormat2Heading",
    "value":"None",
    "sections":[
       {
          "item":"TotalAssets",
          "value":"None",
          "sections":[
             {
                "item":"FixedAssets",
                "value":"None",
                "sections":[
                   {
                      "item":"IntangibleAssets",
                      "value":"None",
                      "sections":[

                      ]
                   },
                   {
                      "item":"PropertyPlantEquipment",
                      "value":"None",
                      "sections":[

                      ]
                   },
                   {
                      "item":"InvestmentsFixedAssets",
                      "value":"None",
                      "sections":[
                         {
                            "item":"LoansToGroupUndertakings",
                            "value":"None",
                            "sections":[

                            ]
                         },
                         {
                            "item":"OwnShares",
                            "value":"None",
                            "sections":[

                            ]
                         }
                      ]
                   },
                   {
                      "item":"InvestmentProperty",
                      "value":"None",
                      "sections":[

                      ]
                   },
                   {
                      "item":"BiologicalAssetsNon-current",
                      "value":"None",
                      "sections":[

                      ]
                   }
                ]
             },
             {
                "item":"CurrentAssets",
                "value":"None",
                "sections":[
                   {
                      "item":"TotalInventories",
                      "value":"None",
                      "sections":[

                      ]
                   },
                   {
                      "item":"BiologicalAssetsCurrent",
                      "value":"None",
                      "sections":[

                      ]
                   },
                   {
                      "item":"Debtors",
                      "value":"None",
                      "sections":[
                         {
                            "item":"PrepaymentsAccruedIncome",
                            "value":"None",
                            "sections":[

                            ]
                         },
                         {
                            "item":"DeferredTaxAssetDebtors",
                            "value":"None",
                            "sections":[

                            ]
                         }
                      ]
                   },
                   {
                      "item":"CurrentAssetInvestments",
                      "value":"None",
                      "sections":[
                         {
                            "item":"InvestmentsInGroupUndertakings",
                            "value":"None",
                            "sections":[

                            ]
                         },
                         {
                            "item":"OwnShares",
                            "value":"None",
                            "sections":[

                            ]
                         }
                      ]
                   },
                   {
                      "item":"CashBankOnHand",
                      "value":"None",
                      "sections":[

                      ]
                   }
                ]
             },
             {
                "item":"PrepaymentsAccruedIncome",
                "value":"None",
                "sections":[

                ]
             }
          ]
       },
       {
          "item":"TotalLiabilities",
          "value":"None",
          "sections":[
             {
                "item":"Equity",
                "value":9014904.0,
                "sections":[

                ]
             },
             {
                "item":"ProvisionsFor",
                "value":"None",
                "sections":[
                   {
                      "item":"RetirementBenefitObligationsSurplus",
                      "value":"None",
                      "sections":[

                      ]
                   }
                ]
             },
             {
                "item":"Creditors",
                "value":"None",
                "sections":[
                   {
                      "item":"UseCurrentNon",
                      "value":"None",
                      "sections":[

                      ]
                   },
                   {
                      "item":"TradeCreditorsTradePayables",
                      "value":"None",
                      "sections":[

                      ]
                   }
                ]
             },
             {
                "item":"AccruedLiabilitiesNot",
                "value":"None",
                "sections":[

                ]
             }
          ]
       }
    ]
 }
]
}
]

我想要实现的是删除具有空sectionsvalue等于None的对象,例如应该从字典中删除整个对象

{
    "item":"IntangibleAssets",
     "value":"None",
      "sections":[]
                  
 }

最终输出应如下所示:

[
  {
    "date":"2017-05-31",
    "sections":[
  {
    "item":"BalanceSheetFormat2Heading",
    "value":"None",
    "sections":[
       {
          "item":"TotalLiabilities",
          "value":"None",
          "sections":[
             {
                "item":"Equity",
                "value":9014904.0,
                "sections":[

                ]
             }
          ]
       }
    ]
 }
]
}
]

我试图检查一个对象是否为空或不使用此功能:

def is_single_element(obj):
    # print(obj)
    if isinstance(obj, dict):
        if "item" in obj and "value" in obj and "sections" in obj:
            if obj["value"] == "None" and len(obj["sections"]) == 0:
                return True
    return False

并递归地遍历 json 并使用以下方法删除那些 obj:

def remove_single_obj(dict_):
    if isinstance(dict_, dict):
        for k, v in list(dict_.items()):
            if is_single_element(v):
                remove_single_obj(v)
    if isinstance(dict_, list):
        for index in range(len(dict_)):
            if is_single_element(dict_[index]):
                dict_.pop(index)
        remove_single_obj(dict_)
    return dict_

但我仍然无法得到所需的结果。非常感谢任何帮助

标签: pythonjsonpython-3.xrecursion

解决方案


这是一个工作代码。
它假设数据根是一个列表,并且列表项是dict,并且所有dict都有'sections'列表,递归。所以不需要通过检查类型isinstance

def delete_emtpy_from_l(l):
    len0 = len(l)
    l[:] = [d for d in l if 'value' in d and d['value'] != 'None' or d['sections']]
    cnt = len0 - len(l)
    for d in l:
        cnt += delete_emtpy_from_l(d['sections'])
    # cnt is how many dict are deleted
    return cnt


# loop until no new dict is deleted
while delete_emtpy_from_l(data):
    pass

pprint(data)

输出:

[{'date': '2017-05-31',
  'sections': [{'item': 'BalanceSheetFormat2Heading',
                'sections': [{'item': 'TotalLiabilities',
                              'sections': [{'item': 'Equity',
                                            'sections': [],
                                            'value': 9014904.0}],
                              'value': 'None'}],
                'value': 'None'}]}]

推荐阅读