Что не так
my_list.append(my_dict)
добавляет ссылку к объекту my_dict
к my_list
. Поэтому в конце for
l oop в вашем примере my_list
- это список ссылок на точно такой же словарь в памяти.
Вы можете убедиться в этом сами, используя функцию id
. id
, по крайней мере, в CPython, в основном дает адрес памяти объекта. Если вы сделаете
article_list.extend(returned_list)
print([id(d) for d in article_list])
, вы получите список идентичных адресов памяти. На моей машине я получаю
[139920570625792, 139920570625792, 139920570625792]
Следствием этого является то, что обновление словаря влияет на «все словари» в вашем списке. (цитаты, потому что на самом деле в вашем списке нет нескольких словарей, просто много раз один и тот же). Таким образом, в конце концов, вам видна только последняя операция обновления.
Хорошее обсуждение ссылок и объектов в Python можно найти в этом ответе { ссылка }
Исправление
Перемещение определения my_dict
внутри for
l oop означает, что вы получаете новый отдельный словарь для каждого элемента my_list
, Теперь операция обновления не повлияет на другие словари в списке, а my_list
- это список ссылок на несколько разных словарей.
def add_entries(list_of_dict):
keys = ['x','y','z']
entry_keys = ['ka','kb','kc']
my_list = []
for item in list_of_dict:
#defining a new dictionary here
my_dict = dict.fromkeys(keys,0)
# conditionally append the entries into the temporary dictionary maintaining desired key names
my_dict.update({a: item[b] for a,b in zip(keys, entry_keys) if b in item})
my_list.append(my_dict)
return my_list