numpy 如何用一个需要另一个数据框的函数填充数据框上的一列

vpfxa7rd  于 2023-08-05  发布在  其他
关注(0)|答案(2)|浏览(107)

我有一个dataframe,其中A列包含三种类型的文本,B列包含日期。
df:

A             B
CPI_x6     01/01/2015
CPI        01/01/2015  
CPI_x9     01/03/2015
CPI        01/05/2015

字符串
我还有另一个 Dataframe VCPI,它的值是:
VCPI:

date          CPI_x6   CPI   CPI_x9
01/01/2015    150      200    300
01/02/2015    153      201    200
01/03/2015    152      180    500
01/04/2015    154      170    100
01/05/2015    155      150    600
01/06/2015    156      160    700
01/07/2015    150      170    600
01/08/2015    151      190    500
01/09/2015    149      200    600
01/10/2015    159      210    800
01/11/2015    158      180    900
01/12/2015    155      190    100


我想在“df”数据框中创建一个“C”列,函数如下:

  • 如果A = CPI_x6,则从B列中的日期开始,使用VCPI值计算6个月后的平均值。
  • 如果A = CPI_x9,则从B列中的日期开始,使用VCPI值计算9个月后的平均值。
  • 如果A = CPI,则取在列B中分配的日期上的 Dataframe VCPI的值。

我不知道该怎么解决这个问题

eqoofvh9

eqoofvh91#

很简单
1.为两者创建df并保存它们。
1.从第1列转换B列,从第2列转换日期,并将其转换为datetime
合并df 1st和该VCPI为:

both_merged_df = pd.merge(df1, vcpi, left_on='B', right_on='date', 
   how='left')

字符串
根据你的条件写一个你想要的函数,例如考虑第一种情况:

if row['A'] == 'CPI_x6':
    return both_merged_df.loc[(both_merged_df['date'] >= row['B']) & (both_merged_df['date'] <= row['B'] + pd.DateOffset(months=6)), 'CPI_x6'].mean()


然后,应用该函数创建一个新列。
此外,我尝试了这个对我来说,这是输出可能会对你有帮助。


的数据

9nvpjoqh

9nvpjoqh2#

您需要计算rolling.mean或每一列,然后执行索引查找:

import re

# ensure datetime
df['B'] = pd.to_datetime(df['B'], dayfirst=False)
VCPI['date'] = pd.to_datetime(VCPI['date'], dayfirst=False)

idx, cols = pd.factorize(df['A'])

df['C'] = (VCPI
  .set_index('date')
  .apply(lambda s: s[::-1].rolling((m.group(0) if (m:=re.search(r'\d+$', s.name)) else '1')+'D',
                                   min_periods=1).mean())
  .loc[df['B'], cols]
  .to_numpy()[np.arange(len(df)), idx]
)

字符串
或者meltmerge

tmp = (VCPI
  .set_index('date')
  .apply(lambda s: s[::-1].rolling((m.group(0) if (m:=re.search(r'\d+$', s.name)) else '1')+'D',
                                   min_periods=1).mean())
  .reset_index().rename(columns={'date': 'B'}).melt('B', var_name='A', value_name='C')
)

out = df.merge(tmp, on=['A', 'B'], how='left')

  • 注意,这将创建一个新的DataFrame。*

输出量:

A          B           C
0  CPI_x6 2015-01-01  153.333333
1     CPI 2015-01-01  200.000000
2  CPI_x9 2015-01-03  588.888889
3     CPI 2015-01-05  150.000000

相关问题