【问题标题】:Python: Why does a function return a dictionary which has all values filled by assignment?Python:为什么函数返回一个字典,其中所有值都由赋值填充?
【发布时间】:2018-10-14 08:09:02
【问题描述】:

我有一个接收列表并输出字典的函数。我正在循环内创建字典并在函数内分配字典值。我想问的一个简化版本如下:

import numpy as np

def get_myDict(tmp_list):
    my_dict = dict.fromkeys(tmp_list, 
                            dict.fromkeys([i**2 for i in tmp_list],0))
    for i in tmp_list:
        my_list = [j for j in np.arange(i)]
        my_dict[i][i**2] = sum(my_list[:]) + i
    return my_dict 

输出如下:

[In 1]: get_myDict([1,2,3,4])
[Out 1]: {1: {1: 1, 4: 3, 9: 6, 16: 10},
          2: {1: 1, 4: 3, 9: 6, 16: 10},
          3: {1: 1, 4: 3, 9: 6, 16: 10},
          4: {1: 1, 4: 3, 9: 6, 16: 10}}

而我希望输出是

{1: {1: 1, 4: 0, 9: 0, 16: 0},
 2: {1: 0, 4: 3, 9: 0, 16: 0},
 3: {1: 0, 4: 0, 9: 6, 16: 0},
 4: {1: 0, 4: 0, 9: 0, 16: 10}}

如果我在函数内定义 my_dict,我会得到所需的输出:

my_dict = {1: {16: 0, 1: 0, 4: 0, 9: 0}, 
           2: {16: 0, 1: 0, 4: 0, 9: 0}, 
           3: {16: 0, 1: 0, 4: 0, 9: 0}, 
           4: {16: 0, 1: 0, 4: 0, 9: 0}}

我相信这在某种程度上与共享引用有关。有人可以解释我在这里做错了什么吗?

【问题讨论】:

  • Python 2.x 还是 3.x?
  • my_dict 中的所有键都具有与其值相同的字典——您传递给fromkeys 的那个。
  • 我正在使用 Python 2.x 。但是,我也尝试了 Python 3.x,结果相同。

标签: python dictionary


【解决方案1】:

你是对的,你实际上是在创建一个带有二次键的字典并多次引用它。

使用 dict 理解(从 Python 2.7 开始):

my_dict = {k: {k2: 0 for k2 in [i**2 for i in tmp_list]} for k in tmp_list}

【讨论】:

    【解决方案2】:

    原因是您有效地将单个值传递给dict.fromkeys() 方法。为了说明你在做什么:

    import numpy as np
    
    def get_myDict(tmp_list):
        value = dict.fromkeys([i**2 for i in tmp_list], 0)
        my_dict = dict.fromkeys(tmp_list, value)
        ...
    

    所以所有的字典都会引用同一个value 字典。

    也许collection.defaultdict 在这里更方便?

    【讨论】:

      猜你喜欢
      • 2011-06-19
      • 2011-03-09
      • 2018-12-06
      • 1970-01-01
      • 1970-01-01
      • 2017-08-02
      • 1970-01-01
      • 2021-11-24
      相关资源
      最近更新 更多