2017-05-18 8 views
2

Ich habe diesen Pandas Datenrahmen zu drehen, die ein einzelne Jahr Snapshot ist:Funktion einzige Pandas Datenrahmen in mehrjährigen Datenrahmen

data = pd.DataFrame({'ID' : (1, 2), 
       'area': (2, 3), 
       'population' : (100, 200), 
       'demand' : (100, 200)}) 

ich dies in eine Zeitreihe machen will, wo Bevölkerung um 10% pro Jahr wächst und die Nachfrage wächst um 20% pro Jahr. In diesem Beispiel mache ich das für zwei zusätzliche Jahre.

Dies sollte der Ausgang sein (Anmerkung: Es enthält eine zusätzliche 'Jahr' Spalte):

output = pd.DataFrame({'ID': (1,2,1,2,1,2), 
       'year': (1,1,2,2,3,3), 
       'area': (2,3,2,3,2,3), 
       'population': (100,200,110,220,121,242), 
       'demand': (100,200,120,240,144,288)}) 

Antwort

0

Setup-Variablen:

k = 5  #Number of years to forecast 
a = 1.20 #Demand Growth 
b = 1.10 #Population Growth 

Prognose Datenrahmen:

df_out = (data[['ID','area']].merge(pd.concat([(data[['demand','population']].mul([pow(a,i),pow(b,i)])).assign(year=i+1) for i in range(k)]), 
          left_index=True, right_index=True) 
        .sort_values(by='year')) 

print(df_out) 

O Ausgabe:

ID area demand population year 
0 1  2 100.00  100.00  1 
1 2  3 200.00  200.00  1 
0 1  2 120.00  110.00  2 
1 2  3 240.00  220.00  2 
0 1  2 144.00  121.00  3 
1 2  3 288.00  242.00  3 
0 1  2 172.80  133.10  4 
1 2  3 345.60  266.20  4 
0 1  2 207.36  146.41  5 
1 2  3 414.72  292.82  5 
0
  • erstellen numpy Array mit [1.1, 1.2], dass ich wiederholen und cumprod
  • eine Reihe von Einsen prepend [1.0, 1.0] zur Berücksichtigung der Anfangsbedingung
  • multiplizieren mit den Werten einer bequem gestapelt pd.Series
  • manipulieren in einen pd.DataFrame Konstruktor
  • aufzuräumen Indizes und was nicht

k = 5 
cols = ['ID', 'area'] 
cum_ret = np.vstack(
    [np.ones((1, 2)), np.array([[1.2, 1.1]] 
)[[0] * k].cumprod(0)])[:, [0, 0, 1, 1]] 
s = data.set_index(cols).unstack(cols) 

pd.DataFrame(
    cum_ret * s.values, 
    columns=s.index 
).stack(cols).reset_index(cols).reset_index(drop=True) 

    ID area demand population 
0 1  2 100.000  100.000 
1 2  3 200.000  200.000 
2 1  2 120.000  110.000 
3 2  3 240.000  220.000 
4 1  2 144.000  121.000 
5 2  3 288.000  242.000 
6 1  2 172.800  133.100 
7 2  3 345.600  266.200 
8 1  2 207.360  146.410 
9 2  3 414.720  292.820 
10 1  2 248.832  161.051 
11 2  3 497.664  322.102