根据分数从字典中删除多余的元组

Remove redundant tuples from dictionary based on the score

提问人:Erwin 提问时间:2/14/2023 更新时间:2/15/2023 访问量:49

问:

我想知道是否有一种快速的方法可以从字典中删除多余的元组。假设我有一本字典,如下所示:

a = {
    'trans': [('pickup', 1.0), ('boat', 1.0), ('plane', 1.0), ('walking', 1.0), ('foot', 1.0), ('train', 0.7455259731472191), ('trailer', 0.7227749512667475), ('car', 0.7759192750865143)],

    'actor': {
    'autori': [('smug', 1.0), ('pol', 1.0), ('traff', 1.0), ('local authori', 0.6894454471465952), ('driv', 0.6121365092485745), ('car', 0.6297345748705596)],

    'fam': [('fa', 1.0), ('mo', 1.0), ('bro', 1.0), ('son', 0.9925431812951816), ('sis', 0.9789254869156859), ('fami', 0.8392597243422916)],

    'fri': [('fri', 1.0), ('compats', 1.0), ('mo', 0.814126196299157), ('neighbor', 0.7433986938516075), ('parent', 0.32202418215134565), ('bro', 0.8496284151715676),  ('fami', 0.6375584385858655), ('best fri', 0.807654599975373)]
            }
    }

例如,在这个字典中,我们有这样的元组:('car', 0.7759192750865143) 用于键 'trans' 和 ('car', 0.6297345748705596) 用于键 'autori'。我想删除元组('car',0.6297345748705596),因为它的分数较低。

我想要的输出是:

new_a = {
    'trans': [('pickup', 1.0), ('boat', 1.0), ('plane', 1.0), ('walking', 1.0), ('foot', 1.0), ('train', 0.7455259731472191), ('trailer', 0.7227749512667475), ('car', 0.7759192750865143)],

    'actor': {
    'autori': [('smug', 1.0), ('pol', 1.0), ('traff', 1.0), ('local authori', 0.6894454471465952), ('driv', 0.6121365092485745)],

    'fam': [('fa', 1.0), ('mo', 1.0), ('bro', 1.0), ('son', 0.9925431812951816), ('sis', 0.9789254869156859), ('fami', 0.8392597243422916)],

    'fri': [('fri', 1.0), ('compats', 1.0), ('neighbor', 0.7433986938516075), ('parent', 0.32202418215134565), ('best fri', 0.807654599975373)]
            }
    }

有没有一种快速的方法可以做到这一点,或者我们仍然需要遍历每个键的所有值?

Python 字典 元组冗余

评论

0赞 cards 2/14/2023
展平迭代器并重新组织它以删除最低的多值项,然后更新原始数据
0赞 Erwin 2/14/2023
您能提出解决方案@cards?

答:

0赞 Dorian Turba 2/14/2023 #1

若要删除较低的值,需要检测重复项、比较、跟踪较高的值,并在发现较大的值时删除值。您想要的算法至少是时间 O(n) 和空间 O(n)。

评论

0赞 Erwin 2/14/2023
你能提出一个简单的解决方案吗?
0赞 Dorian Turba 7/12/2023
不,你做作业;)
1赞 Driftr95 2/15/2023 #2

不确定它是最有效的,但既然您在评论中也提到了“一个简单的解决方案”......

我认为最简单的方法包括遍历每个元组两次:一次是收集最佳分数,然后再次过滤其他所有内容。类似于 [请参阅下面的函数定义]。new_a = onlyBest( a, bestRef=dict(sorted(getAllPairs(a))) )

def getAllPairs(obj):
    if isinstance(obj, tuple) and len(obj)==2: return [obj]
    allPairs = []
    if isinstance(obj, dict): obj = obj.values()
    if hasattr(obj, '__iter__') and not isinstance(obj, str):
        for i in obj: allPairs += getAllPairs(i)
    return allPairs

def onlyBest(obj, bestRef:dict):
    if isinstance(obj, list):
      # if all(isinstance(i, tuple) and len(i)==2 for i in obj):
        return [i for i in obj if not i[1] < bestRef.get(i[0],i[1])]
    if isinstance(obj, dict):
        return {k: onlyBest(v,bestRef) for k, v in obj.items()}
    return obj