2017-12-19 16 views
2

3つの列を参照してデータフレームにラムダ関数を適用しようとしています。条件付き行インデックス付きパンダ - ラムダ関数

最初の行にある場合、Cumulative Totalは、Totalの値に等しくなければなりません。次のロジックに基づいて、Cumulative Totalの列の1つを更新します。 x.shift()['Cumulative Total'] - (x.shift()['Total'] * (x.shift()['Annualized Rate']/1200))

が、私はそう見えるようにCumulative Total列をしたい:それは最初の行がない場合は は、その前の行を参照する次の式を適用する私を投げている何

Total Annualized Rate Cumulative Total 
869  11.04718067  869 
868  5.529953917  861 
871  8.266360505  857 
873  6.872852234  851 
873  8.24742268  846 
874  9.610983982  840 
870  5.517241379  833 
871  8.266360505  829 
868  2.764976959  823 

私が最初の行にいるかどうかをどのように判断できるかです。これはややこしいと聞こえますが、私はパンダにとっては非常に新しく、完全に困惑しています。 ilocは、特定のインデックスの行を取得するためにのみ使用されるように思われるため、動作していないようです。次のように

コードは現在、次のとおりです。

df['Cumulative Total'] = df.apply(lambda x: x['Total'] if x.iloc[0] else x.shift()['Cumulative Total']-(x.shift()['Total']*(x.shift()['Annualized Rate']/1200)),axis=1)

声明if x.iloc[0]が間違っています。それが最初の行であるかどうかをどのように判断できるかについての考えはありますか?

:ご回答ありがとうございます。アレクサンダーの答えは正しかったですが、私は結果が予期されていたことから幾分逸脱していることに気付きました。これらの違いは、使用されるデータフレームが大きくなるほど顕著になりました。

アレクサンダー - 回答を編集してこの問題に対処できますか? vanilla Pythonを使用して、私は以下の結果に到達しました。違いはほとんどありませんが、述べたように、より大きなデータセットでより顕著になることがあります。

total=(869,868,871,873,873,874,870,871,868) 
rate=(11.047181,5.529954,8.266361,6.872852,8.247423,9.610984,5.517241,8.266361,2.764977) 
def f(total,rate): 
    cum = [] 
    for i in range(len(total)): 
     if i == 0: 
      cum.append(total[i]) 
     else: 
      cum.append(float(cum[i-1])-(float(total[i-1])*(rate[i-1]/1200.0))) 
    return cum 
f(total, rate) 

戻り値:

869 
860.9999997591667 
856.9999996991667 
850.99999934 
845.9999995100001 
839.9999992775 
832.9999992641667 
828.9999995391668 
822.9999991800001 

答えて

1

おそらくこれは?

df = df.assign(
    Cumulative_Total=df['Total'].iat[0] 
        - ((df['Total'] * df['Annualized Rate'].div(1200)) 
         .shift() 
         .fillna(0) 
         .cumsum()) 
) 

>>> df 
    Total Annualized Rate Cumulative_Total 
0 869  11.047181    869 
1 868   5.529954    861 
2 871   8.266361    857 
3 873   6.872852    851 
4 873   8.247423    846 
5 874   9.610984    840 
6 870   5.517241    833 
7 871   8.266361    829 
8 868   2.764977    823 
+0

編集前と編集後の両方で、同じエラーが発生しました。 - IndexError:インデックス0は、軸0のサイズが0である。 'axis = 1'を追加する必要がありますか?もしそうなら、どこ? – user1185790

+0

'df ['Total'] .iat [0]'は 'Total'系列の最初の要素にアクセスします。あなたはデータが存在すると確信していますか? 'df.shape'を試してみてください – Alexander

+0

ちょうど気づいた - 私の列には実際にスペースが含まれています - ' df ['累積合計]' – user1185790

0

うこの作品?このソリューションでは、行インデックスを取得するためにx.nameを使用しました。

df['Cumulative Total'] = df.apply(lambda x: x['Total'] if x.name == 0 else x.shift()['Cumulative Total']-(x.shift()['Total']*(x.shift()['Annualized Rate']/1200)),axis=1) 
+0

ValueError:定義済みのインデックスとSeriesに変換できない値を持つフレームを設定できません。私はこれを掘り下げなければならないでしょう。 – user1185790