Irr计算公式

现值与终值

当你投资一笔钱,之后每一年都会收回一些利息,在最后一年将本金和当年的利息全部收回来,这笔投资结束了。那么你到底赚了多少钱呢?首先我们要引入"货币的时间价值"这个概念。货币的时间价值指的是今年我的钱,比如说100元,存入银行吃利息(存入银行吃利息毫无风险),比如说利息是3%,那么明年这100元会变成多少呢?

100 \times (1 + 3\%) = 103

103块,也就是说今年我的100元,可以等价于明年的103元。如果我不取钱,那么到了后年,应该是多少钱呢?

100 \times (1+3\%)^2 = 106.09

比106块稍微多一点点。那么存了n年,应该是多少钱呢?

100 \times (1 + 3\%)^n

很显然,应该是这么算。此时这个公式算出来的值,被称为终值(Final Value, FV),指的某一笔钱最后一期的金额。

刚刚说了,当n=2时,是106.09元,也就是说我把钱存了2年,能得到106.09元,那么反过来看,当我知道以上条件了,我想要知道我需要投资多少钱,才能在2年后得到106.09。很显然,我们应该在一开始投入100元,这个100元就是2年后的106.09的现值(Present Value, PV)

FV = M \cdot (1+r)^n \\ PV = \frac{M}{(1+r)^n}

  • M:Money

我们可以知道,现值和终值是可以互相转化的。由于我们现值通常是投入一笔钱,即支出,因此在金融计算器当中,例如BAII,PV是负数,表示支出。

现金流

现在问题更复杂了些,一开始我投入一笔钱,之后会有若干年,每年年终都收到一笔钱,到最后一年本息付清。那么它的PV应该如何计算呢?

NPV = CF_0 + \frac{CF_1}{1+r} + \frac{CF_2}{(1+r)^2} + ... + \frac{CF_n}{(1+r)^n}

  • CF:Cashflow,现金流

即把每一年的现金流计算其现值,与第0期的投入 CF_0 相加,得到的值,就称其为净现值(Net Presetn Value, NPV)。NPV > 0则代表这笔投资我是赚钱的,如果NPV < 0,则代表这笔投资我是亏钱的。

例如,我第一年投资了100元,之后3年每年收到利息10元,并且在第三年年末,回收了本金100元。假设存银行的利率是3%,那么则有

\begin{aligned} NPV &= (-100) + \frac{10}{1+3\%} + \frac{10}{(1+3\%)^2} + \frac{110}{(1+3\%)^3} \\ &\approx 19.8 \end{aligned}

净现值有19.8,说明赚钱了。

什么是IRR

IRR(Internal Rate of Return),内部收益率,还用刚才的式子解释比较合适

NPV = CF_0 + \frac{CF_1}{1+r} + \frac{CF_2}{(1+r)^2} + ... + \frac{CF_n}{(1+r)^n}

这是计算净现值的式子,假设每一期的现金流我都知道,那么如果NPV=0,即

CF_0 + \frac{CF_1}{1+r} + \frac{CF_2}{(1+r)^2} + ... + \frac{CF_n}{(1+r)^n} = 0

上式中,每一期的CF我都是知道的,如果想让这个式子成立,利率r应该为多少?

之所以提出这个问题,就是我想知道,这一笔投资,如果我不投了,去存银行,那么银行给我多少利息,等价于我这笔投资的收益?

例如

-100 + \frac{10}{1+10\%} + \frac{10}{(1+10\%)^2} + \frac{110}{(1+10\%)^3} = 0

如果我这笔投资,投入了100元,之后3年末都会给我10元的利息,并且第3年末会收回100元的本金,这就实际上相当于存入银行,银行给10%的利息,这二者是等价的,净现值为0。

那么在此处,这里的10%就是这笔投资的内部收益率(IRR)

所谓内部收益率,就是使得一笔投资各期现金流净现值为0的折现率。

内部收益率有一个隐含着的很重要的假设:假设每期收到的现金流能以内部收益率进行再投

为什么会有这种假设?我们从这个净现值的公式就可以看出,这个现金流折现,既能以利率r向前折算为PV,也能以利率r向后折算到FV。它隐含假设了利率r固定不变。并且任何一期的钱可以以利率r来折算到终值。那么这个以内部收益率进行再投的假设就显而易见了。

那么有个问题,如果我这个项目收到的现金我就趴在活期账户上,那么我最终能达到复利10%吗?那当然绝对不可能!这是内部收益率和真正得到的复利不同的地方。

如何计算IRR

Excel

最简单的方法,是使用Excel的IRR函数

Irr计算公式

问题提出

如果只是按个excel,我们的讨论到这里就应该结束了,不过我这里要仔细讨论下,其计算原理到底是什么。下面是IRR的式子

CF_0 + \frac{CF_1}{1+r} + \frac{CF_2}{(1+r)^2} + ... + \frac{CF_n}{(1+r)^n} = 0

每一期的现金流是已知的,净现值为0,未知数只有一个,利率r。怎么把r求出来?

梯度下降法

在解决这个问题前,首先要看一个更为简单的问题。

假设我有一个函数f(x)

y = x^2 + 2x + 1

Irr计算公式

我要寻找到它的最小值,应该怎么去做?

当然对于这个例子而言,我们一眼能看的出来最小值就是x=-1的时刻,y=0。但是我们可能面对更为复杂的情况,因此这里介绍另一种解法。

Irr计算公式

假设我随机选取一点P,由于是随机的,因此这个位置几乎不可能取在最小值,不过没关系,我们研究当前点P。为了简单起见,我们假设P点的X坐标为-4。我们的目标是找到最低点P0。现在我们关注一件事情,就是在P点的导数应该怎么求。

\frac{dy}{dx} = 2x + 2

当x=-4时

\frac{dy}{dx} = 2 \times (-4) + 2 = -6

也就是说,沿着这个函数的切线方向,x增加一个单位,y会降低6个单位。而我们的目标,就是取到y的最小值,那么我们可以尝试让x前进一个单位,用以接近最低点。

x = -4 - \frac{1}{6}\cdot (-6) = -3

看得出来我们用到了一个1/6这个值,因为当前我计算出来的导数为-6,为了简便起见能凑个步长为1,移动到-3,我这里取了一个1/6,当然,严格意义上讲,这个值取多少都可以,我们只是想让x移动一下。

Irr计算公式

现在我们到了这个位置,还按照刚才的办法,计算导数,当然,计算的结果还是负的,从图像上我们就能看得出来,在-3这个位置上,曲线方向还是斜向下的。那么我们就可以总结出来

x_t = x_{t-1} - \eta \frac{dy}{dx}

  • \eta ,学习率,即每次迭代的步长系数,刚才我们取的值是1/6
  • dy/dx :梯度,就是上面说的导数

在上边,当x=-4时,其导数的值为-6,为了方便起见我可以设置学习率 \eta=1/6 ,那么就变成了

\begin{cases} x_t = x_{t-1} - \eta \frac{dy}{dx}\\ x_{t-1} = -4 \\ \eta = \frac{1}{6} \\ \frac{dy}{dx}\Big|_{(x_{t-1})} = -6 \\ \end{cases} \\ x = -4 - \frac{1}{6}\cdot (-6) = -3

我们从任意一点开始,根据当前的导数值的正负号,来决定自变量x应该增加还是减少。那么迭代什么时候停止呢?当导数取值接近0的时候,就是在最低点,迭代就可以停止了。

Irr计算公式

在这个算法中,我们是在尝试去寻找一个函数的最小值,而判断最小值的标准,就是它的导数接近0。因此梯度下降只能找到局部最小。对于简单的一维问题用的是导数,对于多维问题呢?用的就是偏导数,即梯度。

Irr计算公式

用一幅图来形象地表示,就是我们由山顶慢慢走到山脚下的过程。

总结一下,在梯度下降法中,我们需要知道一个损失函数 L(\theta) ,对它的要求有一个

L(\theta) \ge 0, \quad \forall \theta

  • \theta :指的是一个参数数组,而不仅仅指一个单独的参数

我们的目标就是希望调整 \theta ,使得这个损失函数的值达到最小,经过设计的损失函数就是达到最低点:0。

我们需要知道的另一个函数就是这个损失函数的梯度

\frac{\partial L}{\partial \theta}

这样我们就知道应该往哪个方向调整参数 \theta

\theta_t = \theta_{t-1} - \eta \frac{\partial L}{\partial \theta}

用梯度下降来计算IRR

我们之前说到了净现值

NPV = CF_0 + \frac{CF_1}{1+r} + \frac{CF_2}{(1+r)^2} + ... + \frac{CF_n}{(1+r)^n}

这里我们可以用另一种写法

NPV = \sum_{i=0}^n CF_i \cdot (1+r)^{-i}

我们希望调整参数r,来使得它为0,那么看起来NPV本身就有成为损失函数的潜力。但还差一点,就是NPV可能为负,因此,我们把它平方

L(r) = (\sum_{i=0}^n CF_i \cdot (1+r)^{-i})^2

这样一来这就是一个符合我们希望的损失函数了。下面一个问题,就是求它的导数

\frac{dL}{dr} = 2 \cdot (\sum_{i=0}^n CF_i \cdot (1+r)^{-i}) \cdot \Big(\sum_{i=0}^n CF_i(-i)(1+r)^{-i-1}\Big)

好了,损失函数和它的梯度都有了,经过一系列迭代之后,结果将收敛。

在实际进行编程的时候,会发现,r的单位太大了,1就代表了100%,得到的梯度会非常大,这并不利于我们进行梯度下降,因此,需要把r的单位缩小一下,我这里使用的是千分之一。那么损失函数和其导数就要稍微变化一下了

L(r) = (\sum_{i=0}^n CF_i \cdot (1+\frac{r}{1000})^{-i})^2 \\ \frac{dL}{dr} = 2 \cdot (\sum_{i=0}^n CF_i \cdot (1+\frac{r}{1000})^{-i}) \cdot \Big(\sum_{i=0}^n CF_i(-i)(1+\frac{r}{1000})^{-i-1}\Big) \cdot \frac{1}{1000} \\ r_t = r_{t-1} - \eta \frac{dL}{dr}

下面举例,我投资100元,后面三年每年年末都能收到10元利息,并且第三年末回收100元本金。

Irr计算公式
Irr计算公式

cost: 3.128351335715307e-10
interest rate: 99.99992887737645

计算结果收敛到了千分之99.999,即IRR为10%。