我有这个随机函数来计算pi Monte Carlo style:
max=10000000;
format long;
in = 0;
tic
for k=1:max
x = rand();
y = rand();
if sqrt(x^2 + y^2) < 1
in = in + 1;
end
end
toc
calc_pi = 4*in/max
epsilon = abs(pi - calc_pi)
calcPi(100000000);
如果我可以迭代10e100次,这个算法可以与the world record竞争吗?如果是这样,我怎样才能找到给出第N个数字的迭代次数?
答案 0 :(得分:4)
这是计算pi的一个很好的练习,但它可能效率很低。一些评论:
在我喝咖啡之前,我的统计数据已经生锈,但我猜错误会与1 / sqrt(n_guess)
一致。要获得N位数,您需要10^(-N)
的错误,因此您需要大约(10^N)^2
个随机猜测。如果您按照建议进行1e100猜测,那么您只能获得50位数的pi!因此,迭代次数是所需数字的一些指数函数,这是非常慢的。一个好的算法可能是你想要的数字的线性。
由于需要进行大量猜测,您必须开始质疑随机数生成器的质量。
您的算法将受到浮点错误的限制,大约为1e-16左右。计算pi的数字需要某种任意精确数字格式。
要加快算法速度,可以省略sqrt()。
不要使用名为max
的变量,这会覆盖现有函数。使用n_guess左右。
快速而肮脏的测试证明我的理论(咖啡之后):
pie = @(n) 4 * nnz(rand(n,1).^2 + rand(n, 1).^2 < 1) / n;
ntrial = round(logspace(1, 8, 100));
pies = arrayfun(pie, ntrial);
loglog(ntrial, abs(pies - pi), '.k', ntrial, ntrial.^-.5, '--r')
xlabel('ntrials')
ylabel('epsilon')
legend('Monte Carlo', '1 / sqrt(ntrial)')
答案 1 :(得分:1)
简答:不。
根据您的链接,世界纪录是1e13位数。如果您可以运行蒙特卡罗算法来获得10e100样本,您将获得pi的估计值,相对RMS误差为1 / sqrt(10e100)= .3e-50(见下文)。这只是第50位数字的精度。此外,它只是一个“概率”精度:你不会确定前50个数字是正确的;你只能说它们的概率是正确的。
找到N位精度所需的蒙特卡罗样本数量的一般规则是:M蒙特卡罗样本将给出相对RMS精度为1 / sqrt(M)。这意味着估计值与真值相差大约为真值的1 / sqrt(M)分数。为了合理地确信第N个数字是正确的,您需要相对RMS精度略好于10 ^ -N,根据规定的规则要求M = 10 ^(2N)个样本。
因此,如果您想要1e13位数的(概率)精度,则需要10 ^ 2e13蒙特卡罗样本,这是无法管理的。