python處理excel教程實例「python解析json文件並提取」

在測試工作中,通常都會接觸到期望結果數據與實際結果數據一致性比對的測試場景,對於複雜、龐大數據的比對工作。如果依靠人工執行,其成本相當高,難以保障執行結果的一致性(多次執行可能存在偏差),並且重複性極高。因此,通常我們需要考慮如何通過自動化工具實現數據的比對。

本文分享下如何實現Json、字典數據結構的遞歸解析。


JSON的兩種數據結構

1.Key-Value對集合,在Python語言中可以理解為字典(Dict),如下圖。

Python 實現JSON、字典數據結構的遞歸解析

2.有序集合,在Python語言中可以理解為列表(List),如下圖。

Python 實現JSON、字典數據結構的遞歸解析

代碼示例

我們以下面這個較為複雜的Json為例。

test_json = {
    "code": 200,
    "data": [
        {
            "apps": {
                "app_op_seq": [
                    {
                        "action": "點擊",
                        "module_name": "聚划算",
                        "module_type": "resource"
                    }
                ]
            },
            "content": {
                "des": {
                    "company_name": "耐克",
                    "intent": [
                        "full"
                    ]
                },
                "rel": [
                    {
                        "des": {
                            "person_name": "歐陽玖林",
                            "political_status": "金牌會員"
                        },
                        "ont": [
                            "Company",
                            "Person"
                        ],
                        "relIdx": [
                            0,
                            "8-9"
                        ],
                        "relName": "歐陽",
                        "segs": [
                            "耐克籃球鞋"
                        ]
                    }
                ],
                "segs": [
                    "耐克籃球鞋"
                ]
            },
            "content_op": "查詢"
        }
    ]
}

實現源碼

def json_generator(indict, key_value=None):
    """
    遞歸解析 Json 數據
    :param indict:
    :param key_value:
    :return:
    """
    key_value = key_value[:] if key_value else []
    if isinstance(indict, dict):
        for key, value in indict.items():
            tier = - 1
            if isinstance(value, dict) and value != {}:
                if len(value) == 0:
                    yield key_value + [key, '{}']
                else:
                    for d in json_generator(value, key_value + [key]):
                        yield d
            elif isinstance(value, list) and value != []:
                if len(value) == 0:
                    yield key_value + [key, '[]']
                else:
                    for v in value:
                        tier = tier + 1
                        for d in json_generator(v, key_value + [key + '[{0}]'.format(tier)]):
                            yield d
            else:
                yield key_value + [key, value]
    else:
        if not key_value:
            yield indict
        else:
            yield key_value + [indict]

def structure_flow_sub(json_gen_obj):
    """
    解析結果 格式化輸出

    :param json_gen_obj:
    :return: JsonPath:data[0].apps.app_op_seq[0].action
    """
    structure = {}

    for i in json_generator(json_gen_obj):
        if '.'.join(i[:-1]) in structure.keys() and not isinstance(structure['.'.join(i[:-1])], list):
            structure['.'.join(i[:-1])] = [structure['.'.join(i[:-1])]]
            structure['.'.join(i[:-1])].append(i[-1])
        elif '.'.join(i[:-1]) in structure.keys() and isinstance(structure['.'.join(i[:-1])], list):
            structure['.'.join(i[:-1])].append(i[-1])
        else:
            structure['.'.join(i[:-1])] = i[-1]
    return structure

def json_path_parse(json_gen_obj):
    """
    Json路徑解析
    :param json_gen_obj:
    :return:
    """
    structure_List = []
    if isinstance(json_gen_obj, dict):
        structure = structure_flow_sub(json_gen_obj)
        structure_List.append(structure)
        return structure_List
    if isinstance(json_gen_obj, list):
        for i in json_gen_obj:
            result = structure_flow_sub(i)
            structure_List.append(result)
        return structure_List

if __name__ == '__main__':
    all_leaf_node_dict = json_path_parse(test_json)
    line_number = 0
    for k, v in all_leaf_node_dict[0].items():
        line_number += 1
        print("{line_number}  JsonPath:{json_path}   Value:{value} ".format(
            line_number=line_number, json_path=k, value=v))

解析結果如下

1  JsonPath:code   Value:200 
2  JsonPath:data[0].apps.app_op_seq[0].action   Value:點擊 
3  JsonPath:data[0].apps.app_op_seq[0].module_name   Value:聚划算 
4  JsonPath:data[0].apps.app_op_seq[0].module_type   Value:resource 
5  JsonPath:data[0].content.des.company_name   Value:耐克 
6  JsonPath:data[0].content.des.intent[0]   Value:full 
7  JsonPath:data[0].content.rel[0].des.person_name   Value:歐陽玖林 
8  JsonPath:data[0].content.rel[0].des.political_status   Value:金牌會員 
9  JsonPath:data[0].content.rel[0].ont[0]   Value:Company 
10  JsonPath:data[0].content.rel[0].ont[1]   Value:Person 
11  JsonPath:data[0].content.rel[0].relIdx[0]   Value:0 
12  JsonPath:data[0].content.rel[0].relIdx[1]   Value:8-9 
13  JsonPath:data[0].content.rel[0].relName   Value:歐陽 
14  JsonPath:data[0].content.rel[0].segs[0]   Value:耐克籃球鞋 
15  JsonPath:data[0].content.segs[0]   Value:耐克籃球鞋 
16  JsonPath:data[0].content_op   Value:查詢

原創文章,作者:投稿專員,如若轉載,請註明出處:https://www.506064.com/zh-hant/n/251319.html

(0)
打賞 微信掃一掃 微信掃一掃 支付寶掃一掃 支付寶掃一掃
投稿專員的頭像投稿專員
上一篇 2024-12-13 17:22
下一篇 2024-12-13 17:22

相關推薦

發表回復

登錄後才能評論