본문 바로가기
파이썬

파이썬 다양한 깊이의 중첩 사전 값 업데이트

by º기록 2020. 11. 19.
반응형

levelA를 덮어 쓰지 않고 dict update의 내용으로 dict dictionary1을 업데이트하는 방법을 찾고 있습니다.

dictionary1={'level1':{'level2':{'levelA':0,'levelB':1}}}
update={'level1':{'level2':{'levelB':10}}}
dictionary1.update(update)
print dictionary1
{'level1': {'level2': {'levelB': 10}}}

가장 낮은 키 수준 1을 업데이트하기 때문에 업데이트가 level2의 값을 삭제한다는 것을 알고 있습니다.

dictionary1 및 update가 길이를 가질 수 있다는 점을 감안할 때 어떻게 해결할 수 있습니까?

 

해결 방법

 

@FM의 대답에는 올바른 일반적인 아이디어, 즉 재귀 솔루션이 있지만 다소 특이한 코딩과 적어도 하나의 버그가 있습니다. 대신 다음을 권장합니다.

파이썬 2 :

import collections

def update(d, u):
    for k, v in u.iteritems():
        if isinstance(v, collections.Mapping):
            d[k] = update(d.get(k, {}), v)
        else:
            d[k] = v
    return d

파이썬 3 :

import collections.abc

def update(d, u):
    for k, v in u.items():
        if isinstance(v, collections.abc.Mapping):
            d[k] = update(d.get(k, {}), v)
        else:
            d[k] = v
    return d

이 버그는 "update"에 k , v 항목이있을 때 나타납니다. 여기서 v dict 이고 < code> k 는 원래 업데이트되는 사전의 키가 아닙니다. @FM의 코드는 업데이트의이 부분을 "건너 뜁니다"(빈 새 dict 에서 수행하기 때문입니다. t 저장하거나 어디서나 반환했으며 재귀 호출이 반환되면 손실되었습니다).

내 다른 변경 사항은 사소합니다. .get 이 동일한 작업을 더 빠르고 깔끔하게 수행 할 때 if / else 구성에 대한 이유가 없습니다. code> isinstance 는 일반성을 위해 추상 기본 클래스 (구체적인 클래스가 아님)에 가장 잘 적용됩니다.

 

참조 페이지 https://stackoverflow.com/questions/3232943

 

 

반응형

댓글