Python 3.x 将列表中的元组与类似元素合并

Python 3.x 将列表中的元组与类似元素合并,python-3.x,tuples,Python 3.x,Tuples,我必须合并至少包含一个元素的所有元组 tups=[(1,2),(2,3),(8,9),(4,5),(15,12),(9,6),(7,8),(3,11),(1,15)] 第一个元组(1,2)应该与(2,3)、(3,11)、(1,15)、(15,12)合并,因为这些元组中的每一个都包含前一个元组的类似项。所以最后的输出应该是 lst1 = [1,2,3,11,12,15] lst2=[6,7,8,9] since (8,9),(9,6) and (7,8) have matching elemen

我必须合并至少包含一个元素的所有元组

tups=[(1,2),(2,3),(8,9),(4,5),(15,12),(9,6),(7,8),(3,11),(1,15)]
第一个元组(1,2)应该与(2,3)、(3,11)、(1,15)、(15,12)合并,因为这些元组中的每一个都包含前一个元组的类似项。所以最后的输出应该是

lst1 = [1,2,3,11,12,15]
lst2=[6,7,8,9] since (8,9),(9,6) and (7,8) have matching elements
到目前为止,我的代码是:

finlst=[]
for items in range(len(tups)):
    for resid in range(len(tups)):
        if(tups[items] != tups[resid] ):
            if(tups[items][0]==tups[resid][0] or tups[items][0]==tups[resid][1]):
                finlst.append(list(set(tups[items]+tups[resid])))

您可以这样做,使用用匹配元组展开的集合:

tups = [(1, 2), (2, 3), (8, 9), (4, 5), (15, 12), (9, 6), (7, 8), (3, 11), (1, 15)]

groups = []
for t in tups:
    for group in groups:
        # find a group that has at least one element in common with the tuple
        if any(x in group for x in t):
            # extend the group with the items from the tuple
            group.update(t)
            # break from the group-loop as we don’t need to search any further
            break
    else:
        # otherwise (if the group-loop ended without being cancelled with `break`)
        # create a new group from the tuple
        groups.append(set(t))


# output
for group in groups:
    print(group)

由于此解决方案按顺序迭代原始元组列表一次,因此对于连接不直接可见的输入,这将不起作用。为此,我们可以使用以下解决方案,只要仍然有效,就可以使用该解决方案组合组:

tups = [(1, 2), (3, 4), (1, 4)]

import itertools

groups = [set(t) for t in tups]
while True:
    for a, b in itertools.combinations(groups, 2):
        # if the groups can be merged
        if len(a & b):
            # construct new groups list
            groups = [g for g in groups if g != a and g != b]
            groups.append(a | b)

            # break the for loop and restart
            break
    else:
        # the for loop ended naturally, so no overlapping groups were found
        break

我找到了解决方案,更多的是关于连通性的图论问题

我们可以使用NetworkX实现这一点,它几乎保证是正确的:

def uniqueGroup(groups):
#     grp=[]
#     for group in groups:
#         grp.append(list(group))
#     l=groups

    import networkx 
    from networkx.algorithms.components.connected import connected_components


    def to_graph(groups):
        G = networkx.Graph()
        for part in groups:
            # each sublist is a bunch of nodes
            G.add_nodes_from(part)
            # it also imlies a number of edges:
            G.add_edges_from(to_edges(part))
        return G

    def to_edges(groups):
        """ 
            treat `l` as a Graph and returns it's edges 
            to_edges(['a','b','c','d']) -> [(a,b), (b,c),(c,d)]
        """
        it = iter(groups)
        last = next(it)

        for current in it:
            yield last, current
            last = current    

    G = to_graph(groups)
    return connected_components(G)
输出:

tups = [(1, 2),(3,4),(1,4)]
uniqueGroup(tups)

{1, 2, 3, 4}

不清楚你在问什么。为什么要将
(1,15)
(3,11)
合并<代码>(1,15)没有与
(3,15)
相同的元素,而
(3,11)
没有与第一个元素
(1,2)
相同的元素。所以我想说,这里的逻辑并不清楚。您是在尝试将最后一个匹配作为下一个匹配的基础(例如
(1,2)->(2,3)->(3,4)
)还是将所有匹配基于第一个元组(例如
(1,2)->(2,5)->(6,1)
)?当元组列表为tups=[(1,2)、(3,4)、(1,4)],则失败,预期输出为{1,2,3,4},但是ur代码返回{1,2,4},{3,4}
tups = [(1, 2),(3,4),(1,4)]
uniqueGroup(tups)

{1, 2, 3, 4}