pandas 对齐两个嵌套框列并保持顺序(不按字典顺序重新排序

pftdvrlh  于 2023-09-29  发布在  其他
关注(0)|答案(3)|浏览(99)

设A和B为两个 Dataframe 列:
| 你好|Foo|嘿|酒吧|世界|
| --|--|--|--|--|
| 你好|酒吧|Doo|世界|星星|
| --|--|--|--|--|
我想获得一个dataframe C的列,它包含了所有的唯一列,但是列的顺序必须和以前一样。
| 你好|Foo|酒吧|嘿|Doo|世界|星星|
| --|--|--|--|--|--|--|
换句话说:如果A是一个较旧版本的 Dataframe ,B是一个较新版本的 Dataframe ,如何得到一个 Dataframe C,它以一种与A(或B)保持一致的顺序的方式跟踪A删除的列(不存在于B中)和B添加的列(不存在于A中)?“.
方法align可以混合两个数据框列,但它不保留原始顺序,顺序是字典顺序。

ee7vknir

ee7vknir1#

假设你真的想在两个索引中保持原来的顺序(并假设没有循环模式),你可以使用下面的算法:

A = pd.DataFrame(columns=['Hello', 'Foo', 'Hey', 'Bar', 'World'])
B = pd.DataFrame(columns=['Hello', 'Bar', 'Doo', 'World', 'Star'])

def merge(A, B):
    sA = set(A)
    sB = set(B)
    out = {}
    while sA or sB:  # while items are left in A or B
        for a in A:          # take from A while not in B
            sA.discard(a)
            if a in sB:
                break
            out.setdefault(a)
        for b in B:          # take from B while not in A
            sB.discard(b)
            if b in sA:
                break
            out.setdefault(b)
    return list(out)

out = merge(A, B)

输出量:

['Hello', 'Foo', 'Hey', 'Bar', 'Doo', 'World', 'Star']

通用解决方案

或者,您可以使用图论,使用networkx.from_edgelistitertools.pairwise构建一个有向图,其中所有连续列对都是边,然后使用dag_longest_path找到最长路径:

import networkx as nx
from itertools import pairwise

dfs = [A, B]
G = nx.from_edgelist((pair for pairs in map(pairwise, dfs) for pair in pairs),
                     create_using=nx.DiGraph)
C_cols = nx.dag_longest_path(G)

输出量:

['Hello', 'Foo', 'Hey', 'Bar', 'Doo', 'World', 'Star']

图表:

yh2wf1be

yh2wf1be2#

我会把它简化为一个列表解析问题。首先获取列列表:

a_cols = A.columns
b_cols = B.columns

然后应用您的匹配逻辑:

c_cols = []
for i in range(len(a)):
    c_cols.append(a_cols[i])
    c_cols.append(b_cols[i])

然后,您可以通过执行C.columns = c_cols来重新排序C Dataframe 。

ikfrs5lh

ikfrs5lh3#

a = A.columns.tolist()
b = B.columns.tolist()
i = 0
j = 0
x = []
while i <len(a) or j<len(b):
  if i<len(a):
    if a[i] not in x: x.append(a[i])
    i+=1
  if j<len(b):
    if b[j] not in x: x.append(b[j])
    j+=1
df = pd.DataFrame(columns=x)

相关问题