【问题标题】:Simulate 1,000 geometric brownian motions in MATLAB在 MATLAB 中模拟 1,000 个几何布朗运动
【发布时间】:2013-09-12 03:51:38
【问题描述】:

我目前拥有模拟几何布朗运动的代码,由 http://www-math.bgsu.edu/~zirbel/sde/matlab/index.html 提供。

但是,我想生成 1,000 个模拟并将它们显示在图表中。

我目前生成单个模拟的代码如下:

% geometric_brownian(N,r,alpha,T) simulates a geometric Brownian motion 
% on [0,T] using N normally distributed steps and parameters r and alpha

function [X] = geometric_brownian(N,r,alpha,T)

t = (0:1:N)'/N;                   % t is the column vector [0 1/N 2/N ... 1]

W = [0; cumsum(randn(N,1))]/sqrt(N); % S is running sum of N(0,1/N) variables

t = t*T;
W = W*sqrt(T);

Y = (r-(alpha^2)/2)*t + alpha * W;

X = exp(Y);

plot(t,X);          % plot the path
hold on
plot(t,exp(r*t),':');
axis([0 T 0 max(1,exp((r-(alpha^2)/2)*T+2*alpha))])
title([int2str(N) '-step geometric Brownian motion and its mean'])
xlabel(['r = ' num2str(r) ' and alpha = ' num2str(alpha)])
hold off

【问题讨论】:

    标签: matlab simulation


    【解决方案1】:

    该代码不能直接用于模拟 1,000 条路径/模拟。不幸的是,它还没有被矢量化。做你想做的最简单的方法是使用for 循环:

    N = 1e3;
    r = 1;
    alpha = 0.1;
    T = 1;
    npaths = 1e3;          % Number of simulations
    
    rng(0);                % Always set a seed
    X = zeros(N+1,npaths); % Preallocate memory
    for i = 1:n
        X(:,i) = geometric_brownian(N,r,alpha,T);
        hold on
    end
    t = T*(0:1:N).'/N;
    plot(t,exp(r*t),'r--');
    

    这是相当缓慢和低效的。您将需要大量修改该函数以对其进行矢量化。可以提高性能的一件事是,如果您至少从函数内部删除了绘图代码并在循环之后单独运行它。

    另一种选择可能是在我的SDETools toolbox 中使用sde_gbm 函数,它是完全矢量化的并且速度更快:

    N = 1e3;
    r = 1;
    alpha = 0.1;
    T = 1;
    npaths = 1e3;        % Number of simulations
    
    t = T*(0:1:N)/N;     % Time vector
    y0 = ones(npaths,1); % Vector of initial conditions, must match number of paths
    opts = sdeset('RandSeed',0,'SDEType','Ito'); % Set seed
    y = sde_gbm(r,alpha,t,y0,opts);
    
    figure;
    plot(t,y,'b',t,y0*exp(r*t),'r--');
    xlabel('t');
    ylabel('y(t)');
    title(['Geometric Brownian motion and it's mean: ' int2str(npaths) ...
           ' paths, r = ' num2str(r) ', \alpha = ' num2str(alpha)]);
    

    在任何一种情况下,都会得到一个看起来像这样的图

                  

    【讨论】:

      【解决方案2】:

      要执行 1000 次模拟,直接的方法是:

      Nsims = 1000;
      N=10^15;         % set to length of individual sim                    
      r = 1;
      alpha = 0.1;
      T = 1;
      
      t = (0:1:N)'/N;                   
      t = (T*(r-(alpha^2)/2))*t;
      W = cat(1,zeros(1,Nsims),cumsum(randn(N,Nsims))); 
      W = W*(sqrt(T)*alpha/sqrt(N));
      Y = repmat(t,1,Nsims) + W;
      X = exp(Y);
      

      绘图和以前一样

      plot(t,X);             % plots ALL 1000 paths
      %   plot(t,X(:,paths));   % use instead to show only selected paths (e.g. paths =[1 2 3])
      hold on
      plot(t,exp(r*t),':');
      axis([0 T 0 max(1,exp((r-(alpha^2)/2)*T+2*alpha))])
      title([int2str(N) '-step geometric Brownian motion and its mean'])
      xlabel(['r = ' num2str(r) ' and alpha = ' num2str(alpha)])
      hold off
      

      对于相对较短(小)的模拟集,循环您的代码或执行上述操作应该可以。对于重型模拟,您可能会受益于 Horchler 承诺的速度优势。

      【讨论】:

      • 我认为 OP 是在询问如何为 0 到 T 生成 1,000 个独立模拟(或布朗运动用语中的路径),而不是单个模拟的 1,000 个时间步长。
      猜你喜欢
      • 1970-01-01
      • 2011-08-12
      • 2017-12-14
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-04-22
      相关资源
      最近更新 更多