2017-11-08 6 views
1

Ich habe einen Datenrahmen mit Waldbestand id, Baumart, Höhe und Volumen:Gewichtete durchschnittliche Pandas

import pandas as pd 

df=pd.DataFrame.from_items([('STAND_ID',[1,1,2,3,3,3]),('Species',['Conifer','Broadleaves','Conifer','Broadleaves','Conifer','Conifer']), 
          ('Height',[20,19,13,24,25,18]),('Volume',[200,100,300,50,100,10])]) 

    STAND_ID  Species Height Volume 
0   1  Conifer  20  200 
1   1 Broadleaves  19  100 
2   2  Conifer  13  300 
3   3 Broadleaves  24  50 
4   3  Conifer  25  100 
5   3  Conifer  18  10 

Ich möchte von Stand-ID GROUPBY und unstack und volumengewichtete mittlere Höhe berechnen, so dass ich versuchen:

newdf=df.groupby(['STAND_ID','Species']).mean().unstack() 

      Height    Volume   
Species Broadleaves Conifer Broadleaves Conifer 
STAND_ID           
1    19.0 20.0  100.0 200.0 
2    NaN 13.0   NaN 300.0 
3    24.0 21.5  50.0 55.0 

Die Höhen sind natürlich nicht volumengewichtet. Wie kann ich sie belasten? Wie dies für STAND_ID 3 und Conifer:

(25 * 100 + 18 * 10)/(100 + 10) = 24,4

+1

Können Sie „Volumengewicht“ erklären? Was ist das für eine Berechnung? –

+0

@ScottBoston Ich habe die Frage bearbeitet – BERA

+0

Ich habe eine Antwort geschrieben, vorausgesetzt, Sie brauchen nicht volumengewichtete Lautstärke .. Lassen Sie mich wissen, wenn dies nicht die Ausgabe ist, die Sie erwarten. –

Antwort

4

Wenn Lambda-Funktionen anwenden können, sind verwirrend auch mit einer Funktionsdefinition verwendet werden. (Und es ist auch eine Funktion numpy.average gewichteten Mittelwert berechnen)

import numpy as np 
def weighted_average(group): 
    weights = group['Volume'] 
    height = group['Height'] 

    return np.average(height,weights=weights) 

df.groupby(['STAND_ID','Species']).apply(func = weighted_average).unstack() 
2

Wenn ich richtig verstehe, wäre eine Möglichkeit, die Durchführung ein groupby mit apply:

df 
    STAND_ID  Species Height Volume 
0   1  Conifer  20  200 
1   1 Broadleaves  19  100 
2   2  Conifer  13  300 
3   3 Broadleaves  24  50 
4   3  Conifer  25  100 
5   3  Conifer  18  10 

df.groupby(['STAND_ID','Species']).apply(lambda x: (x['Height'] * x['Volume'].div(x['Volume'].sum())).sum()).unstack() 

Species Broadleaves Conifer 
STAND_ID       
1    19.0 20.000000 
2     NaN 13.000000 
3    24.0 24.363636 
Verwandte Themen