当 M 很大时返回 nan(ind)

Returning nan(ind) when M is big

本文关键字:nan ind 返回      更新时间:2023-10-16

M很大时,它返回sum_payoff = nan(ind)。我不明白为什么,只有当M真的很大时。

int M = 50000;
double K = 32; // Strike price
double r = 0.05; // Interest Rate
double sigma = 0.2; // Underlying's volatility
double T = 5.0 / 12.0; // 5 Months Maturity
double sum_payoff(0.0);
for (int i(0); i < M; i++) {
double S_T = S*exp((r - pow(sigma, 2))*T + sigma * sqrt(T)*rand_normal());
sum_payoff += max(S_T - K, 0.0);
cout << sum_payoff << endl;
}
cout << "Sum payoff : " << sum_payoff << endl;

PS : rand_normal()按照标准正态定律 N(0,1) 返回一个随机数。

您的计数器i属于int类型,它只能容纳某些范围数据类型范围,如果M大于此范围,则i的值将没有意义,您可能会得到负值,这会弄乱整个循环。

此外,当您分配一个大于数据类型范围的值时,它将被截断。例如

int M = 99999999999;
std::cout<<M; // it won't be 99999999999

假设

int M = 50000;

代表你对大数的定义,我会说你在rand_normal中有一个错误,或者没有使用你期望的 max(),或者未能初始化 S,你的编译器没有默认为零。

如果 rand_normal() 正确且 S 是有效值,则根据您拥有的代码,sum_payoff应该比 50000 * S 高约 10%。

推理:exp(...) 中除 rand_normal() 之外的所有项都是常量,将循环中的赋值行减少到

double S_T = S*exp(0.004166 + 0.129099*rand_normal());

这给出了 0.004166 到 0.133265 的输入范围,相应的 exp() 输出范围为 1.004175 到 1.142553。 由于 S 未被循环修改,因此无论 S 是什么(假设它是> 0),结果平均都会比 50000 * S 高约 10%。

检查以验证它是否正在调用您希望调用的 max() 函数;在不同的命名空间中可能有多个 max() 定义,具体取决于您用于构建此函数的内容。 如果调用了错误的 max(),则结果可能是不可预测的。

检查rand_normal的定义,因为如果您关闭了浮点异常(或者正在使用不支持它们的编译器),则意外结果(例如存储为 nan(ind) 的零除错误)可能会进行计算。

如果这两个都不是问题,请仔细检查 S 的定义(无论数据类型是什么),并确保它已正确初始化,并且 50000*S 不足以溢出双精度数据类型。