您好, 欢迎来到 !    登录 | 注册 | | 设为首页 | 收藏本站

用Python(pandas)计算可变现金流量IRR

用Python(pandas)计算可变现金流量IRR

您可以使用scipy.optimize.fsolve

给定初始估计值,返回由func(x)= 0定义的(非线性)方程的根。

首先定义将成为func参数的函数fsolve。由于您的内部收益率,现金流量和年数,这是净现值。(使用NumPy矢量化。)

import numpy as np
def npv(irr, cfs, yrs):  
    return np.sum(cfs / (1. + irr) ** yrs)

一个例子:

cash_flow = np.array([-2., .5, .75, 1.35])
years = np.arange(4)

# A guess
print(npv(irr=0.10, cfs=cash_flow, yrs=years))
0.0886551465064

现在使用fsolve

from scipy.optimize import fsolve
def irr(cfs, yrs, x0):
    return np.asscalar(fsolve(npv, x0=x0, args=(cfs, yrs)))

您的内部收益率是:

print(irr(cfs=cash_flow, yrs=years, x0=0.10))
0.12129650313214262

您可以确认这使您的NPV为0:

res = irr(cfs=cash_flow, yrs=years, x0=0.10)
print(np.allclose(npv(res, cash_flow, years), 0.))
True

所有代码一起:

import numpy as np
from scipy.optimize import fsolve

def npv(irr, cfs, yrs):  
    return np.sum(cfs / (1. + irr) ** yrs)

def irr(cfs, yrs, x0, **kwargs):
    return np.asscalar(fsolve(npv, x0=x0, args=(cfs, yrs), **kwargs))

为了使其与您的熊猫示例兼容,只需使用

cash_flow = df.cash_flow.values
years = df.years_ago.values

更新:您的问题中的值似乎有点荒谬(如果IRR甚至存在,您的IRR将会是一个天文数字),但是这是您的运行方式:

cash_flow = np.array([-3.60837e+06, 31462, 1.05956e+06, -1.32718e+06, -4.46554e+06])    
years_ago = np.array([4.09167, 4.09167, 3.63333, 3.28056, 3.03889])

print(irr(cash_flow, years_ago, x0=0.10, maxfev=10000))
1.3977721900669127e+82

第二次更新:您的代码中有一些次要的错别字,您的实际$流量和计时结果对无意义的IRR起作用,但是下面是您要执行的操作。例如,请注意您有一个ID,其中包含一个负交易,即负无限IRR。

for i, df in df_tran.groupby('id'):
   cash_flow = df.cash_flow.values
   years = df.years.values
   print('id:', i, 'irr:', irr(cash_flow, years, x0=0.))

id: 978237 irr: 347.8254979851405
id: 1329483 irr: 3.2921314448062817e+114
id: 1365051 irr: 1.0444951674872467e+25
python 2022/1/1 18:28:32 有188人围观

撰写回答


你尚未登录,登录后可以

和开发者交流问题的细节

关注并接收问题和回答的更新提醒

参与内容的编辑和改进,让解决方法与时俱进

请先登录

推荐问题


联系我
置顶