繁体   English   中英

从python列表中删除不必要的项目

[英]Remove unnecessary items from python list

我有一个包含 8 个唯一元组的列表,每个元组的大小为 2。从那里我找到了大小为 4 的所有可能组合。现在,我有一个列表列表,在每个子列表中我正好有 4 个元组。 就像是 -

[[(1, 2), (4, 5), (223, 456), (111, 345)], [...], ...]

主要列表可能在哪里 -

[(1, 2), (4, 5), (223, 456), (111, 345), (123, 4), (23, 89), (999, 888), (895, 569)]

这些实际上是 2D 平面中点的坐标,我将 8 个点分成两组,每组 4 个。 因此,如果我有一个包含 4 分的列表,则意味着我已经拥有其他 4 分。 因此,对于 4 点的每个组合,我都试图从列表中删除其他 4 点。

以下作品——

def generate_all_points(points, size):
    from itertools import combinations

    all_combinations = combinations(points, size)
    return (list(all_combinations))    

def generate_4points(points):

    all_4points = generate_all_points(points, 4)
    print (len(all_4points))
    print ("ALL POINTS -\t", points)
    for point_set in all_4points:

        to_remove = list(set(points).difference(set(point_set)))
        for item in all_4points:
            if (len(set(to_remove).difference(item)) == 0):
                all_4points.remove(item)

        print ("Main -\t", point_set, "\nTo Remove -\t", to_remove)
        #all_4points.remove(list(set(points).difference(set(point_set))))
    print (len(all_4points))

我尝试只使用set.difference但它重新排序列表项,因此我无法直接删除它们。 我在注释行中尝试过。 我所做的是从 8 中找到剩余的 4 点,然后如果 4 和组合列表中的任何项目的集合差的长度为零,那么这意味着在一起,这两个 4 点的集合匹配唯一8,因此我删除了该特定项目。

有没有办法在没有循环等的情况下在一两行中直接实现这一点?

提前致谢。

更好的解决方案是首先避免生成不需要的组合。

这实际上相当容易,因为组合是按顺序生成的。 我们只需要拿他们的前半部分。 8个(8*7*6*5/(4*3*2))中4个点有70个组合,所以我们只保留前35个。

一个演示,使用从 1 到 8 的数字而不是元组以提高可读性:

from itertools import combinations, islice

l = [1, 2, 3, 4, 5, 6, 7, 8]

nb_combinations = 70
print(list(islice(combinations(l, 4), nb_combinations//2)))

输出:

[(1, 2, 3, 4), (1, 2, 3, 5), (1, 2, 3, 6), (1, 2, 3, 7), (1, 2, 3, 8), 
(1, 2, 4, 5), (1, 2, 4, 6), (1, 2, 4, 7), (1, 2, 4, 8), (1, 2, 5, 6), 
(1, 2, 5, 7), (1, 2, 5, 8), (1, 2, 6, 7), (1, 2, 6, 8), (1, 2, 7, 8),
(1, 3, 4, 5), (1, 3, 4, 6), (1, 3, 4, 7), (1, 3, 4, 8), (1, 3, 5, 6),
(1, 3, 5, 7), (1, 3, 5, 8), (1, 3, 6, 7), (1, 3, 6, 8), (1, 3, 7, 8),
(1, 4, 5, 6), (1, 4, 5, 7), (1, 4, 5, 8), (1, 4, 6, 7), (1, 4, 6, 8),
(1, 4, 7, 8), (1, 5, 6, 7), (1, 5, 6, 8), (1, 5, 7, 8), (1, 6, 7, 8)]

您可以看到所有这 35 个组合都包含第一个值 1,因此我们确定它们中没有一个是该集合中另一个的补充。

所以,你的函数可以写成:

from itertools import combinations, islice

def generate_4points(points):
    # we only keep the first 35 combinations out of 70
    return list(islice(combinations(points, 4), 35))

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM