Вы можете сделать это более компактно, но я настрою несколько промежуточных столбцов, чтобы логика была ясной. Во-первых, я собираюсь установить образец набора данных с несколькими взлетами и падениями.
import pandas as pd
prices = [50.00,46.75,44.25,50.00,59.25,66.50,
29.25,44.25,59.25,61.00,64.25,65.25]
dates = pd.date_range('01-31-1983','12-31-1983', freq='m')
df = pd.DataFrame({'Month End Price':prices}, index=dates)
Это приводит к кадру данных, который выглядит так:
Month End Price
1983-01-31 50.00
1983-02-28 46.75
1983-03-31 44.25
1983-04-30 50.00
1983-05-31 59.25
1983-06-30 66.50
1983-07-31 29.25
1983-08-31 44.25
1983-09-30 59.25
1983-10-31 61.00
1983-11-30 64.25
1983-12-31 65.25
И это:
Вы можете рассчитать месячные колебания цены следующим образом:
df['Monthly Returns'] = df['Month End Price'].diff()/df['Month End Price']
Мы хотим реализовать все выгоды и избежать всех потерь, от которых японять. Я установил столбец множителей, который равен 1 для месяцев, когда мы должны были избежать потерь, и в основном равен 1 + df['Monthly Returns']
для месяцев с прибылью. Затем я вычисляю столбец Cash
как кумулятивное произведение столбца Multiplier
, умноженного на $ 41, который был нашим основным. Существует соблазн использовать цикл for
, но с Pandas, каждый раз, когда вы видите for
, часто есть более быстрый, встроенный, как cumprod
:
df['Multiplier'] = df['Monthly Returns'].apply(lambda x: max(x, 0)) + 1
df['Cash'] = df['Multiplier'].cumprod() * 41
Как только все этосделано, у нас есть что-то похожее на:
Month End Price Monthly Returns Multiplier Cash
1983-01-31 50.00 NaN NaN 41.000000
1983-02-28 46.75 -0.069519 1.000000 41.000000
1983-03-31 44.25 -0.056497 1.000000 41.000000
1983-04-30 50.00 0.115000 1.115000 45.715000
1983-05-31 59.25 0.156118 1.156118 52.851941
1983-06-30 66.50 0.109023 1.109023 58.613995
1983-07-31 29.25 -1.273504 1.000000 58.613995
1983-08-31 44.25 0.338983 1.338983 78.483145
1983-09-30 59.25 0.253165 1.253165 98.352296
1983-10-31 61.00 0.028689 1.028689 101.173878
1983-11-30 64.25 0.050584 1.050584 106.291623
1983-12-31 65.25 0.015326 1.015326 107.920614
И значение позиций выглядит так: