【问题标题】:iterate through 2 dictionaries, if value occurs in one, count down the int value in other then remove key if count = 0遍历 2 个字典,如果值出现在一个字典中,则倒数另一个字典中的 int 值,如果 count = 0 则删除键
【发布时间】:2020-01-27 00:11:39
【问题描述】:

我有 2 个字典对象:

members = {'member3': ['PCP3'], 'member4': ['PCP1'], 'member11': ['PCP2'], 'member12': ['PCP3']}
providers = {'PCP1': 2, 'PCP2': 2, 'PCP3': 1, 'PCP4': 3, 'PCP5': 4}

我想遍历两者,并且每次出现“成员”字典的值时,从该特定提供者的计数中减去一个。如果提供者的计数达到零,则将它们从“提供者”字典中删除,并从“成员”字典中随机挑选一个成员。所以在这种情况下 member3 或 member12 将被踢出,因为没有足够的位置。

例如,如果 member3 赢得了随机折腾,结果将如下所示:

members = {'member3' : 'PCP3', 'member4': 'PCP1' , 'member11': PCP2}
providers = {'PCP1: 1, 'PCP2' : 1, 'PCP4': 3, 'PCP5' : 4}

我已经尝试从这个开始,但这个问题超出了我的能力范围

from collections import defaultdict
query_dict=defaultdict(set)
for (k,v), (k2,v2) in zip(members_reduced.items(), PCPs.items()):
    query_dict[k[v]].subtract(k2[v2])

这会报错

TypeError:字符串索引必须是整数

我也试过了:

for (k,v), (k2,v2) in zip(members_reduced.items(), PCPs.items()):
if members_reduced[v] == PCPs[k2]:
    PCPs[v2] -= 1

有错误

TypeError: unhashable type: 'list'

我不知道如果第一部分正确,我将如何输入随机条件。这是我在工作中需要的更大模型中的一个更小的模型

【问题讨论】:

  • 迭代members.items()然后执行if value in providers: providers[value] -= 1等等会简单得多。
  • 很难为您的暂定解决方案提供提示,因为您在输入和暂定解决方案中使用不同的名称,因此它们不会在没有猜测的情况下运行,这会阻止其他人调试它们或复制您的观察到的行为没有不必要的猜测。请考虑调整您的问题以生成minimal reproducible example
  • 对不起,我不确定你在哪里指的是不同的名字。输出字典具有相同的名称。结构也是相同的,只是成员减少了,因为一个成员被引导并且提供者的数量更少
  • PCPsmembers_reduced 在您的解决方案中使用但未定义...

标签: python dictionary counter


【解决方案1】:

解决任务的一种方法是:

import random


members = {'member3': ['PCP3'], 'member4': ['PCP1'], 'member11': ['PCP2'], 'member12': ['PCP3']}
providers = {'PCP1': 2, 'PCP2': 2, 'PCP3': 1, 'PCP4': 3, 'PCP5': 4}


to_remove = []
for member, provider_list in members.items():
    provider = provider_list[0]
    if provider in providers:
        providers[provider] -= 1
        if providers[provider] == 0:
            providers.pop(provider)
            to_remove.append(provider)
for provider in to_remove:
    candidates = [
        member for member, provider_list in members.items()
        if provider == provider_list[0]]
    candidate = random.sample(candidates, 1)[0]
    members.pop(candidate)


print(members)
# {'member4': ['PCP1'], 'member11': ['PCP2'], 'member12': ['PCP3']}
print(providers)
# {'PCP1': 1, 'PCP2': 1, 'PCP4': 3, 'PCP5': 4}```

基本上,我们分两遍解决问题:

  • 在第一遍中,我们修改了计数器,当计数器达到 0 时,我们将 member 标记为删除
  • 在第二遍中,我们根据标记为移除的内容移除成员

【讨论】:

  • 我如何将变量 candidate 更改为不仅仅是 1,而是该提供者所需的数量与提供者实际开放槽数之间的差异是什么?
  • @BenSmith 我不会从dict 中删除负数,而不是创建一个新的to_remove 列表,而是循环遍历原始dict 并删除与负数一样多的项目计数表明。如果您在执行此操作时遇到困难,也许您可​​以问另一个问题。
  • no to_remove 列出需要遍历的提供程序。我现在卡住的地方是如果to_remove 中有多个成员,那么有两组成员,我如何创建这些组的列表。喜欢,[['member3', 'member12'], ['member14', 'member15', 'member16']]
  • 我认为你应该问一个新问题。仅从上面的 cmets 中,我不明白您在追求什么。
猜你喜欢
  • 2022-11-22
  • 2017-07-06
  • 2021-09-03
  • 1970-01-01
  • 2011-03-10
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2010-12-14
相关资源
最近更新 更多