itertools.product消除重复的反向元组 [英] itertools.product eliminating repeated reversed tuples

查看:59
本文介绍了itertools.product消除重复的反向元组的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

昨天我问了一个问题,感谢蒂姆·彼得斯(Tim Peters),问题已解决.问题在这里;

I asked a question yesterday and thanks to Tim Peters, it is solved. The question is here;

itertools.product消除重复元素

新问题是此问题的进一步版本.这次,我将在元组内部生成元组.这是一个例子;

The new question is further version of this. This time I will generate tuples inside of tuples. Here is an example;

lis = [[(1,2), (3,4)], [(5,2), (1,2)], [(2,1), (1,2)]]

当我在itertools.product函数中使用它时,这就是我所得到的,

When I use it in itertools.product function this is what I get,

((1, 2), (5, 2), (2, 1))
((1, 2), (5, 2), (1, 2))
((1, 2), (1, 2), (2, 1))
((1, 2), (1, 2), (1, 2))
((3, 4), (5, 2), (2, 1))
((3, 4), (5, 2), (1, 2))
((3, 4), (1, 2), (2, 1))
((3, 4), (1, 2), (1, 2))

我想以某种方式更改它,如果序列内部有(a,b),那么它就不能具有(b,a).在此示例中,如果查看此序列((3, 4), (1, 2), (2, 1)),则其内部有(1,2)和(2,1).因此,结果中不应考虑此序列((3, 4), (1, 2), (2, 1)).

I want to change it in a way that if a sequence has (a,b) inside of it, then it can not have (b,a). In this example if you look at this sequence ((3, 4), (1, 2), (2, 1)) it has (1,2) and (2,1) inside of it. So, this sequence ((3, 4), (1, 2), (2, 1)) should not be considered in the results.

正如我所说,我之前曾问过类似的问题,在这种情况下,它没有考虑重复的元素.我尝试使其适应我的问题.这是修改后的代码.旧版本中的已更改部分将包含在注释中.

As I said, I asked similar question before, in that case it was not considering duplicate elements. I try to adapt it to my problem. Here is modified code. Changed parts in old version are taken in comments.

def reverse_seq(seq):
    s = []
    for i in range(len(seq)):
        s.append(seq[-i-1])         
    return tuple(s)


def uprod(*seqs):  
    def inner(i):
        if i == n:
            yield tuple(result)
            return
        for elt in sets[i] - reverse:
            #seen.add(elt)
            rvrs = reverse_seq(elt)
            reverse.add(rvrs)
            result[i] = elt
            for t in inner(i+1):
                yield t
            #seen.remove(elt)
            reverse.remove(rvrs)

    sets = [set(seq) for seq in seqs]
    n = len(sets)
    #seen = set()
    reverse = set()
    result = [None] * n
    for t in inner(0):
        yield t

我认为该代码应该可以工作,但是输入lis = [[(1,2), (3,4)], [(5,2), (1,2)], [(2,1), (1,2)]]时出现错误.我不明白我哪里错了.

In my opinion this code should work but I am getting error for the input lis = [[(1,2), (3,4)], [(5,2), (1,2)], [(2,1), (1,2)]]. I could not understand where I am wrong.

for i in uprod(*lis):
    print i

输出为

((1, 2), (1, 2), (1, 2))
Traceback (most recent call last):
  File "D:\Users\SUUSER\workspace tree\sequence_covering _array\denemeler_buraya.py", line 39, in <module>
    for i in uprod(*lis):
  File "D:\Users\SUUSER\workspace tree\sequence_covering _array\denemeler_buraya.py", line 32, in uprod
    for t in inner(0):
  File "D:\Users\SUUSER\workspace tree\sequence_covering _array\denemeler_buraya.py", line 22, in inner
    for t in inner(i+1):
  File "D:\Users\SUUSER\workspace tree\sequence_covering _array\denemeler_buraya.py", line 25, in inner
    reverse.remove(rvrs)
KeyError: (2, 1)

谢谢

推荐答案

问题在于,即使在您之前(c5>中> 已在reverse中,您无条件执行reverse.remove(rvrs),也是如此) )添加了它.因此插入:

The problem is that you unconditionally do reverse.remove(rvrs), even if rvrs was already in reverse before you (redundantly) added it. So insert:

            remove_later = rvrs not in reverse

之前:

            reverse.add(rvrs)

并将删除代码更改为:

            if remove_later:
                reverse.remove(rvrs)

然后输出为:

((1, 2), (1, 2), (1, 2))
((1, 2), (5, 2), (1, 2))
((3, 4), (1, 2), (1, 2))
((3, 4), (5, 2), (1, 2))
((3, 4), (5, 2), (2, 1))

与此无关,您可以扔掉reverse_seq()函数并改为编写它:

Unrelatedly, you can throw away the reverse_seq() function and write this instead:

            rvrs = elt[::-1]

这篇关于itertools.product消除重复的反向元组的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆