Python 将函数应用于列

Python 将函数应用于列,python,python-3.x,pandas,Python,Python 3.x,Pandas,我在将几个函数应用于数据帧时遇到一些问题 我创建了一个示例代码来说明我要做的事情。可能有一种比我现在做的更好的方法来完成这个特定的功能,但是我正试图为我的问题找到一个通用的解决方案,因为我使用了几个功能,而不仅仅是如何最有效地完成这个特定的事情 基本上,我有一个示例数据帧,如下所示(df1): 一个示例数据帧如下所示(df2): df2中“SumVol”列中的值应填入df1中“Volume”列中的值之和,直到在df2中第一次看到“Price”(df1)列中的值,并且df1中的日期与df2中的日期

我在将几个函数应用于数据帧时遇到一些问题

我创建了一个示例代码来说明我要做的事情。可能有一种比我现在做的更好的方法来完成这个特定的功能,但是我正试图为我的问题找到一个通用的解决方案,因为我使用了几个功能,而不仅仅是如何最有效地完成这个特定的事情

基本上,我有一个示例数据帧,如下所示(df1):

一个示例数据帧如下所示(df2):

df2中“SumVol”列中的值应填入df1中“Volume”列中的值之和,直到在df2中第一次看到“Price”(df1)列中的值,并且df1中的日期与df2中的日期匹配

期望输出:

    Ticker      Date  Price  SumVol
0   AAPL  20200508    1.2    300
1   TSLA  20200508    2.2    500
出于某种原因,我无法获得此输出,因为我可能在试图将函数应用于数据帧的代码行中出错。我希望这里有人能帮助我

完整示例代码,包括示例数据帧:

import pandas as pd

df1 = pd.DataFrame({'Ticker': ['AAPL', 'AAPL', 'AAPL', 'AAPL', 'AAPL', 'AAPL', 'TSLA', 'TSLA', 'TSLA', 'TSLA', 'TSLA', 'TSLA'],
                'Date': [20200501, 20200501, 20200501, 20200502, 20200502, 20200502, 20200501, 20200501, 20200501, 20200502, 20200502, 20200502],
               'High': [1.5, 1.2, 1.3, 1.4, 1.2, 1.1, 2.5, 2.2, 2.3, 2.4, 2.2, 2.1],
                'Volume': [150, 100, 150, 130, 170, 160, 250, 200, 250, 230, 270, 260]})
print(df1)

df2 = pd.DataFrame({'Ticker': ['AAPL', 'TSLA'],
               'Date': [20200501, 20200502],
                'Price': [1.4, 2.2],
                'SumVol': [0,0]})

print(df2)

def VolSum(ticker, date, price):
    df11 = pd.DataFrame(df1)
    df11 = df11[df11['Ticker'] == ticker]
    df11 = df11[df11['Date'] == date]
    df11 = df11[df11['High'] < price]

    df11 = pd.DataFrame(df11)
    return df11.Volume.sum

df2['SumVol'].apply(VolSum(df2['Ticker'], df2['Date'], df2['Price']), inplace=True).reset_index(drop=True, inplace=True)
print(df2)
将熊猫作为pd导入
df1=pd.DataFrame({'Ticker':['AAPL','AAPL','AAPL','AAPL','AAPL','AAPL','TSLA','TSLA','TSLA','TSLA'],
‘日期’:[20200501、20200501、20200501、20200502、20200502、20200502、20200501、20200501、20200501、20200502、20200502、20200502、20200502],
‘高’:[1.5,1.2,1.3,1.4,1.2,1.1,2.5,2.2,2.3,2.4,2.2,2.1],
“卷”:[150100150130170160250200250230270260])
打印(df1)
df2=pd.DataFrame({'Ticker':['AAPL','TSLA'],
“日期”:[20200501,20200502],
“价格”:[1.4,2.2],
“SumVol”:[0,0]})
打印(df2)
def VolSum(股票代码、日期、价格):
df11=局部数据帧(df1)
df11=df11[df11['Ticker']==Ticker]
df11=df11[df11['Date']==Date]
df11=df11[df11[高]<价格]
df11=局部数据帧(df11)
返回df11.Volume.sum
df2['SumVol'].应用(VolSum(df2['Ticker'],df2['Date'],df2['Price']),原地=真)。重置索引(drop=真,原地=真)
打印(df2)

失败的第一个原因是函数以
返回df11.Volume.sum
(不带括号), 所以只返回sum函数,而不是它的执行结果

另一个原因是,您可以将函数应用于数据帧的每一行, 但必须传递axis=1参数。但是:

  • 要应用的函数应具有一个参数-当前行
  • 其结果可在所需列下替换
失败的第三个原因是df2包含例如不存在的日期 在df1中,您不太可能找到任何匹配的行

如何获得预期结果-方法1 首先,df2必须包含可能与df1匹配的值。 我将df2定义为:

然后我将您的函数更改为:

def VolSum(row):
    df11 = pd.DataFrame(df1)
    df11 = df11[df11['Ticker'] == row.Ticker]
    df11 = df11[df11['Date'] == row.Date]
    df11 = df11[df11['High'] < row.Price]
    return df11.Volume.sum()
结果是:

  Ticker      Date  Price  SumVol
0   AAPL  20200501    1.4     250
1   TSLA  20200502    2.3     530
如何获得预期结果-方法2 但更简洁、更优雅的方法是将求和函数定义为:

def VolSum2(row):
    return df1.query('Ticker == @row.Ticker and '
        'Date == @row.Date and High < @row.Price').Volume.sum()

结果当然是一样的。

谢谢你的回答,verry解释得很好,效果很好。很抱歉示例df中的错误,我会更新我的原始帖子以备将来查看
def VolSum(row):
    df11 = pd.DataFrame(df1)
    df11 = df11[df11['Ticker'] == row.Ticker]
    df11 = df11[df11['Date'] == row.Date]
    df11 = df11[df11['High'] < row.Price]
    return df11.Volume.sum()
df2['SumVol'] = df2.apply(VolSum, axis=1)
  Ticker      Date  Price  SumVol
0   AAPL  20200501    1.4     250
1   TSLA  20200502    2.3     530
def VolSum2(row):
    return df1.query('Ticker == @row.Ticker and '
        'Date == @row.Date and High < @row.Price').Volume.sum()
df2['SumVol'] = df2.apply(VolSum2, axis=1)