首页 > 解决方案 > 展平 Python Dict 并且仅在不唯一时更改键

问题描述

扁平化 Python 字典有很多很好的解决方案,但是当值是字典时,大多数递归方法似乎会自动将“父键”添加到键中(无论嵌套键是否是迄今为止唯一的) - 就像在这个解决方案。这是在嵌套时自动将父键添加到键的扁平化功能。

def flatten_dict(item, parent_key='', sep='_'):
    final = []
    for key, val in item.items():
        new_key = parent_key + sep + key if parent_key else key        
        if isinstance(val, dict):
            final.extend(flatten_dict(val, parent_key=new_key).items())
        else:        
            final.append((new_key, val))
    return dict(final)

我试图将一组“使用过的键”传递给 flatten_dict 并且仍然将父键添加到键中(我想它们在递归中被多次传递并被标记为已使用)。有没有办法使用递归仅在 key 不唯一的情况下将 parent_key 添加到 key 中?

例如:

flatten_dict({'a':1, 'b': {'a': 1, 'c': 1}}) 

返回:

{'a': 1, 'b_a':1, 'b_c': 1}

但理想情况下,我想:

{'a': 1, 'b_a': 1, 'c': 1} # because 'c' is unique 

谢谢你的帮助!

标签: pythonrecursion

解决方案


我建议使用“累加器”字典作为输入参数而不是列表。这可以有效地查找密钥是否已经存在。

def flat_dict(d, acc=None, parent_key=None, sep="_"):
    out = dict() if acc is None else acc
    for k, v in d.items():
        if type(v) is dict:
            flat_dict(v, out, parent_key=str(k))
        else:
            if k in out:
                k = parent_key + sep + str(k)
            out[k] = v

    return out

如果你所有的键都已经是字符串,你当然可以放弃str强制转换。


推荐阅读