python时间数据合并_python – 如何基于最近的日期合并两个数据帧

该博客介绍了如何在Python中合并两个数据帧,特别是当需要根据最近的日期匹配数据时。作者使用了scikit-learn的NearestNeighbors库来找到每个数据点最近的日期,并在数据帧中添加这一信息,然后通过标准合并操作完成合并。文中给出了详细的步骤和示例代码。
摘要由CSDN通过智能技术生成

我不认为有一种快速,单行的方式来做这种事情,但我相信最好的方法是这样做:

>使用df2中相应组中最接近的日期向df1添加一列

>在这些上调用标准合并

随着数据大小的增长,除非你做一些复杂的事情,否则这个“最接近日期”的操作会变得相当昂贵.我喜欢使用scikit-learn的NearestNeighbor代码来做这类事情.

我已经将一种解决方案放在一起,这种解决方案应该相对较好地扩展.

首先我们可以生成一些简单的数据:

import pandas as pd

import numpy as np

dates = pd.date_range('2015', periods=200, freq='D')

rand = np.random.RandomState(42)

i1 = np.sort(rand.permutation(np.arange(len(dates)))[:5])

i2 = np.sort(rand.permutation(np.arange(len(dates)))[:5])

df1 = pd.DataFrame({'Code': rand.randint(0, 2, 5),

'Date': dates[i1],

'val1':rand.rand(5)})

df2 = pd.DataFrame({'Code': rand.randint(0, 2, 5),

'Date': dates[i2],

'val2':rand.rand(5)})

我们来看看这些:

>>> df1

Code Date val1

0 0 2015-01-16 0.975852

1 0 2015-01-31 0.516300

2 1 2015-04-06 0.322956

3 1 2015-05-09 0.795186

4 1 2015-06-08 0.270832

>>> df2

Code Date val2

0 1 2015-02-03 0.184334

1 1 2015-04-13 0.080873

2 0 2015-05-02 0.428314

3 1 2015-06-26 0.688500

4 0 2015-06-30 0.058194

现在让我们编写一个apply函数,使用scikit-learn将最近的日期列添加到df1:

from sklearn.neighbors import NearestNeighbors

def find_nearest(group, match, groupname):

match = match[match[groupname] == group.name]

nbrs = NearestNeighbors(1).fit(match['Date'].values[:, None])

dist, ind = nbrs.kneighbors(group['Date'].values[:, None])

group['Date1'] = group['Date']

group['Date'] = match['Date'].values[ind.ravel()]

return group

df1_mod = df1.groupby('Code').apply(find_nearest, df2, 'Code')

>>> df1_mod

Code Date val1 Date1

0 0 2015-05-02 0.975852 2015-01-16

1 0 2015-05-02 0.516300 2015-01-31

2 1 2015-04-13 0.322956 2015-04-06

3 1 2015-04-13 0.795186 2015-05-09

4 1 2015-06-26 0.270832 2015-06-08

最后,我们可以通过直接调用pd.merge将它们合并在一起:

>>> pd.merge(df1_mod, df2, on=['Code', 'Date'])

Code Date val1 Date1 val2

0 0 2015-05-02 0.975852 2015-01-16 0.428314

1 0 2015-05-02 0.516300 2015-01-31 0.428314

2 1 2015-04-13 0.322956 2015-04-06 0.080873

3 1 2015-04-13 0.795186 2015-05-09 0.080873

4 1 2015-06-26 0.270832 2015-06-08 0.688500

请注意,第0行和第1行都匹配相同的val2;考虑到您描述所需解决方案的方式,这是预期的.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值