我来自 R,老实说,这是使用 R data.tables 在一行中完成的最简单的事情,并且对于大型数据表来说,该操作也相当快。但是我真的很难用Python实现它。前面提到的用例都不适合我的应用程序。当前的主要问题是 Python 解决方案中的内存使用情况,我将在下面解释。
问题:我有两个大型 DataFrame df1 和 df2 (每个大约 50M-100M 行),我需要根据两个条件将 df2 的两列(或 n 列)合并到 df1 :
1) df1.id = df2.id(通常合并的情况)
2) df2.value_2A
import numpy as np
import pandas as pd
df1 = pd.DataFrame({'id': [1,1,1,2,2,3], 'value_1': [2,5,7,1,3,4]})
df2 = pd.DataFrame({'id': [1,1,1,1,2,2,2,3], 'value_2A': [0,3,7,12,0,2,3,1], 'value_2B': [1,5,9,15,1,4,6,3]})
df1
Out[13]:
id value_1
0 1 2
1 1 5
2 1 7
3 2 1
4 2 3
5 3 4
df2
Out[14]:
id value_2A value_2B
0 1 0 1
1 1 3 5
2 1 7 9
3 1 12 15
4 2 0 1
5 2 2 4
6 2 3 6
7 3 1 3
desired_output
Out[15]:
id value_1 value_2A value_2B
0 1 2 NaN NaN
1 1 5 3.0 5.0
2 1 7 7.0 9.0
3 2 1 0.0 1.0
4 2 3 2.0 4.0
5 2 3 3.0 6.0
6 3 4 NaN NaN
现在,我知道这可以通过首先以“左”方式合并 df1 和 df2 然后过滤数据来完成。但就扩展而言,这是一个可怕的解决方案。我有 50M x 50M 行,其中有多个 id 重复项。这将创建一些巨大的数据框,我必须对其进行过滤。
## This is NOT a solution because memory usage is just too large and
## too many oprations deeming it extremely inefficient and slow at large scale
output = pd.merge(df1, df2, on='id', how='left') ## output becomes very large in my case
output.loc[~((output['value_1'] >= output['value_2A']) & (output['value_1'] <= output['value_2B'])), ['value_2A', 'value_2B']] = np.nan
output = output.loc[~ output['value_2A'].isnull()]
output = pd.merge(df1, output, on=['id', 'value_1'], how='left')
这太低效了。我将大型数据集合并两次以获得所需的输出,并在此过程中创建大量数据帧。哎呀!
将其视为事件的两个数据帧,我试图将它们匹配在一起。也就是说,标记 df1 的事件是否已发生在 df2 的事件内。 df1 和 df2 中的每个 id 都有多个事件。 df2 的事件不是相互排斥的。条件连接确实需要在连接时发生,而不是之后。
这在 R 中很容易完成:
## in R realm ##
require(data.table)
desired_output <- df2[df1, on=.(id, value_2A <= value_1, value_2B >= value_1)] #fast and easy operation
有什么方法可以在Python中做到这一点吗?