合并Pandas中的公共列值会产生不正确的datafram

2024-06-28 21:04:30 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在尝试基于一个公共列合并pandas中的2个数据帧。在阅读有关合并的文档时,我所做的每一件事都暗示了dataframes应该在指定的列上合并,同时只保留公共值。它当然会保留公共值,但会生成一个庞大的数据帧,对于“左”数据帧中的每个索引,它本质上是一个完整的“右”数据帧。你知道吗

我左边的数据框是

left
Out[325]: 
     A   B   C   D MergeThis
0   38  43  20  34       -N2
1   14  44  23  91       -N2
2   55  50  30  92       -N2
3   29  20  56   0       -N2
4   61   6  38  44       -N2
5   18  61  30   7       -N2
6   67  45  60  81       -N2
7    7  53  60  72       +N2
8   15  46   0  82       +N2
9    6  90  83  36       +N2
10   0  87  64  82       +N2
11  13  22  13  39       +N2
12  65  88  50  34       +N2
13  35  31  72  34       +N2

我右边的数据框是

right
Out[326]: 
    E   F   G   H MergeThis
0  22  81  97  28       +N2
1  20   4  44  48       +N2
2  19  41  52  25       +N2
3  30  37  66  24       +N2
4  32  40  56  92       +N2
5  95  76  91  31       +N2
6  36  66  17  85       +N2

显然,我试图在“MergeThis”列上进行合并,这样我就得到了+N2值的组合,以及来自“left”和“right”的列。然而,我最终得到的却是一些奇怪的东西:

left.merge(right, on='MergeThis')
Out[327]: 
     A   B   C   D MergeThis   E   F   G   H
0    7  53  60  72       +N2  22  81  97  28
1    7  53  60  72       +N2  20   4  44  48
2    7  53  60  72       +N2  19  41  52  25
3    7  53  60  72       +N2  30  37  66  24
4    7  53  60  72       +N2  32  40  56  92
5    7  53  60  72       +N2  95  76  91  31
6    7  53  60  72       +N2  36  66  17  85
7   15  46   0  82       +N2  22  81  97  28
8   15  46   0  82       +N2  20   4  44  48
9   15  46   0  82       +N2  19  41  52  25
10  15  46   0  82       +N2  30  37  66  24
11  15  46   0  82       +N2  32  40  56  92
12  15  46   0  82       +N2  95  76  91  31
13  15  46   0  82       +N2  36  66  17  85
14   6  90  83  36       +N2  22  81  97  28
15   6  90  83  36       +N2  20   4  44  48
16   6  90  83  36       +N2  19  41  52  25
17   6  90  83  36       +N2  30  37  66  24
18   6  90  83  36       +N2  32  40  56  92
19   6  90  83  36       +N2  95  76  91  31
20   6  90  83  36       +N2  36  66  17  85
21   0  87  64  82       +N2  22  81  97  28
22   0  87  64  82       +N2  20   4  44  48
23   0  87  64  82       +N2  19  41  52  25
24   0  87  64  82       +N2  30  37  66  24
25   0  87  64  82       +N2  32  40  56  92
26   0  87  64  82       +N2  95  76  91  31
27   0  87  64  82       +N2  36  66  17  85
28  13  22  13  39       +N2  22  81  97  28
29  13  22  13  39       +N2  20   4  44  48
30  13  22  13  39       +N2  19  41  52  25
31  13  22  13  39       +N2  30  37  66  24
32  13  22  13  39       +N2  32  40  56  92
33  13  22  13  39       +N2  95  76  91  31
34  13  22  13  39       +N2  36  66  17  85
35  65  88  50  34       +N2  22  81  97  28
36  65  88  50  34       +N2  20   4  44  48
37  65  88  50  34       +N2  19  41  52  25
38  65  88  50  34       +N2  30  37  66  24
39  65  88  50  34       +N2  32  40  56  92
40  65  88  50  34       +N2  95  76  91  31
41  65  88  50  34       +N2  36  66  17  85
42  35  31  72  34       +N2  22  81  97  28
43  35  31  72  34       +N2  20   4  44  48
44  35  31  72  34       +N2  19  41  52  25
45  35  31  72  34       +N2  30  37  66  24
46  35  31  72  34       +N2  32  40  56  92
47  35  31  72  34       +N2  95  76  91  31
48  35  31  72  34       +N2  36  66  17  85

它基本上为我的“右”数据帧的每个索引创建了一个重复的数据帧。你知道吗

一方面,我知道如何做另一种变通方法,用更多的代码获得我想要的数据帧,并将其中一个数据帧分解得更多一些,以便合并“更漂亮”。然而,我真的很想知道为什么会这样?我希望将来能够使用合并功能,但我不完全了解pandas试图做什么来产生这种效果。你知道吗

非常感谢您的帮助。你知道吗


Tags: 数据代码文档rightpandasonmergeout
1条回答
网友
1楼 · 发布于 2024-06-28 21:04:30

结果看起来是正确的。联接条件是将leftMergeThis等于+N2的每一行联接到具有该匹配条件的right的每一行。在每个数据帧中有7个这样的行,结果在输出中有49行是行集的笛卡尔积。你知道吗

请注意,DataFrame.merge的合并类型是leftrightinnerouter,它们决定了用于连接的键集,而不是限制哪些行将与哪些其他行匹配。默认的inner只意味着在leftright之间使用包含在联接列中的值的交集,反正就是+N2。如果您使用right,您将得到相同的结果,因为正确的数据帧只包含该列的+N2。同样地,如果您使用leftouter,它们在本例中恰好相同,因为这两种情况都会导致可能的匹配集基于-N2+N2,并且您将从+N2的所有成对匹配中获得49行,再加上-N2的其他行(但没有其他匹配),以及NaN列的值,在这种情况下,这些值将来自right)。你知道吗

听上去,你可能已经预料到right中的7行+N2会被附加到left,而其他行则被NaN填充。要实现这一点,应该使用连接而不是基于合并的连接。你知道吗

下面是一个使用pandas.concat的类似玩具数据的示例(完成后只需删除额外的MergeThis列即可)

In [42]: right
Out[42]:
   C  D MergeThis
0  1  2       +N2
1  3  4       +N2
2  5  6       +N2
3  7  8       +N2

In [43]: left
Out[43]:
    A   B MergeThis
0   1   2       -N2
1   3   4       -N2
2   5   6       +N2
3   7   8       +N2
4   9  10       +N2
5  11  12       +N2

In [44]: right.index = left[left.MergeThis == '+N2'].index.values

In [45]: right
Out[45]:
   C  D MergeThis
2  1  2       +N2
3  3  4       +N2
4  5  6       +N2
5  7  8       +N2

In [46]: pandas.concat([left, right], axis=1)
Out[46]:
    A   B MergeThis    C    D MergeThis
0   1   2       -N2  NaN  NaN       NaN
1   3   4       -N2  NaN  NaN       NaN
2   5   6       +N2  1.0  2.0       +N2
3   7   8       +N2  3.0  4.0       +N2
4   9  10       +N2  5.0  6.0       +N2
5  11  12       +N2  7.0  8.0       +N2

相关问题 更多 >