【问题标题】:Intersection and Difference of two dictionaries两本词典的交集和差集
【发布时间】:2016-10-01 10:00:22
【问题描述】:

给定两个字典,我想查看它们的相交和差异,并对相交的元素执行 f 函数并对唯一元素执行 g,这就是我如何找出 d1 和 d2 所在的唯一元素和相交元素的方法两个字典,我如何打印出 d_intersection 和 d_difference 作为元组内的字典?输出应该是这样的({intersecting keys,values}, {difference keys,values}) 例如:给定

d1 = {1:30, 2:20, 3:30, 5:80}

d2 = {1:40, 2:50, 3:60, 4:70, 6:90}

输出应该是({1: 70, 2: 70, 3: 90}, {4: 70, 5: 80, 6: 90})

dic = {}
d_intersect = set(d1) & set(d2)
d_difference =  set(d1) ^ set(d2)
for i in d_intersect:
    dic.update({i : f(d1[i],d2[i])})
for j in d_difference:
    dic.update({j : g(d1[j],d2[j])})

谁能告诉我哪里出错了,为什么我的代码给出了关键错误 4?

【问题讨论】:

  • 一个建议:你的问题很乱,不好理解,代码看起来很奇怪。那是什么编程语言?当你说你期望某个输出但你没有提供输入时,你几乎不可能理解你在寻找什么。
  • 抱歉,已编辑。它的 python 和一个测验的问题之一,我试图解决它。我对 python 很陌生,所以我的代码看起来很丑
  • 从输出看起来你想要一个包含两个字典的元组。函数 dict_interdif 给出一个字典。

标签: python dictionary


【解决方案1】:

您会得到 4KeyError,因为 ^ 会寻找 对称差异,这意味着密钥 对两者都是唯一的 em>,键都不在中。你也不需要创建集合,你可以使用调用.keys返回的view object

d1 = {1: 30, 2: 20, 3: 30, 5: 80}

d2 = {1: 40, 2: 50, 3: 60, 4: 70, 6: 90}

 # d1.keys() ^ d2 -> {4, 5, 6}, 4, 6 unique to d2, 5 unique to d1.
symm = {k: d1.get(k, d2.get(k)) for k in d1.keys() ^ d2}
inter = {k: d2[k] + d1[k] for k in d1.keys() & d2}

d1.get(k, d2.get(k)) 适用于 对称差异,因为当我们从 d2 获得唯一密钥时,它会捕获。

python2 的代码略有不同,您需要将.keys 替换为.viewkeys 以获得view object:

 {k: d1.get(k, d2.get(k)) for k in d1.viewkeys() ^ d2}
 {k: d2[k] + d1[k]  for k in d1.viewkeys() & d2}

要获得两个集合之间的差异,即 a 中有什么但 b 中没有,您需要-

In [1]: d1 = {1: 30, 2: 20, 3: 30, 5: 80}

In [2]: d2 = {1: 40, 2: 50, 3: 60, 4: 70, 6: 90}

In [3]: {k: d2[k] for k in d2.keys() - d1}
Out[3]: {4: 70, 6: 90}

In [4]: {k: d1[k] for k in d1.keys() - d2}
Out[4]: {5: 80}
In [5]: d2.keys() - d1 # in d2 not in d1
Out[5]: {4, 6}

In [6]: d1.keys() - d2 # in d1 not in d2
Out[6]: {5}

In [7]: d1.keys() ^ d2 # unique to either
Out[7]: {4, 5, 6}

对称的差异就像做差异的并集:

In [12]: d1.keys() - d2 |  d2.keys() - d1
Out[12]: {4, 5, 6}

所有运算符都在 python docs 中进行了讨论,Set_(mathematics) 上的 wiki 页面也为您提供了一个很好的概述。

【讨论】:

  • 所以对称差异只有在两个字典中都不存在但只有一个时才会捕获一个值?我想要两个字典中不存在于另一个字典中的任何元素。就像 {5:80} 没有出现在 d2 中,我同样想要 {4:70, 6:90} 因为它们没有出现在 d1 中。我可以研究这些集合和集合的交集的任何好的资源吗?谢谢你的回答顺便说一句
  • @user6820366,两个集合的对称差异将包含任一集合中对该集合唯一的元素。我添加了一些进一步的例子。
  • 我明白了,这是有道理的,对称差异是每个字典中键的差异的并集。谢谢,这非常有用:D
  • @user6820366,恰好在 a 中,而不是在 b 中,反之亦然。只需将对称差异视为每个集合所独有的。
【解决方案2】:

这是一种方法,尽管可能有更有效的方法。

d1 = {1:30, 2:20, 3:30, 5:80}
d2 = {1:40, 2:50, 3:60, 4:70, 6:90}

d_intersect = {} # Keys that appear in both dictionaries.
d_difference = {} # Unique keys that appear in only one dictionary.

# Get all keys from both dictionaries.
# Convert it into a set so that we don't loop through duplicate keys.
all_keys = set(d1.keys() + d2.keys()) # Python2.7
#all_keys = set(list(d1.keys()) + list(d2.keys())) # Python3.3

for key in all_keys:
    if key in d1 and key in d2:
        # If the key appears in both dictionaries, add both values
        # together and place it in intersect.
        d_intersect[key] = d1[key] + d2[key]
    else:
        # Otherwise find out the dictionary it comes from and place
        # it in difference.
        if key in d1:
            d_difference[key] = d1[key]
        else:
            d_difference[key] = d2[key]

输出:

{1:70, 2:70, 3:90}

{4:70, 5:80, 6:90}

【讨论】:

  • 你能否解释一下代码是如何工作的,我知道这有点太多了,但我真的很想知道这段代码是如何工作的,所以我可以根据你的代码制作自己的代码。谢谢。
  • 当然,我将包括 cmets。
  • 非常感谢!行 all_keys = set(d1.keys() + d2.keys()) 给出错误 TypeError: unsupported operand type(s) for +: 'dict_keys' and 'dict_keys'
  • 你的 d1 和 d2 值是多少?
  • 我在问题中提出的相同值,它们根本没有改变,我试图在 pythontutor 上运行这段代码,它给了我这个错误。
猜你喜欢
  • 1970-01-01
  • 2011-09-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-01-26
  • 2018-06-11
  • 1970-01-01
相关资源
最近更新 更多