使用parfor扫描一组ODE的初始条件

时间:2016-03-11 01:24:24

标签: matlab parameters ode parfor ode45

我目前正在尝试使用parfor来扫描一系列由ode45求解的微分方程的初始条件。代码使用两个嵌套的for循环工作正常,但我希望parfor可以使进程更有效。不幸的是,我遇到了一个问题,求解器能够解决矩阵中的一个组合,表示一系列变量的初始条件,但其他组合似乎将其初始值全部设置为0,而不是指定的值在初始条件下。这可能与我需要创建一个零的矩阵(' P')以及结果将被写入的事实有关,可能会覆盖初始条件(?)任何帮助都将非常感激

谢谢, 凯尔

function help(C, R)

A = 0.01;
B = 0.00;
C = [0.001,0.01];
D = 0.00;
R = [1e-10,1e-9];

[CGrid,RGrid] = meshgrid(C,R);

parfor ij = 1 : numel(CGrid)
        c2 = [A; B; CGrid(ij); D; RGrid(ij)];
        [t,c] = ode45('ode_sys',[0:1:300],c2);
        for k=1:length([0:1:300])
            for l=1:length(c2)
                if c(k,l)<0
                    c(k,l)=0;
                end
            end
        end

    P = zeros(301,5,numel(R),numel(C));
    temp = zeros(301,5);      
    temp(:,1) = c(:,1);
    temp(:,2) = c(:,2);
    temp(:,3) = c(:,3);
    temp(:,4) = c(:,4);
    temp(:,5) = c(:,5);
    P(:,:,ij)=temp;

    parsave('data.mat', P);
    end
end

1 个答案:

答案 0 :(得分:0)

您有一个错误,并且有一些简化代码的机会。

parfor循环中,您有这一行P = zeros(301,5,numel(R),numel(C));,它会在每次迭代时用全零覆盖P。把它放在parfor循环之前。

第一个双重for循环使得c的负数元素为零可以使用max(c,0)完成,这应该更有效。您也可以直接P(:,:,ij)=c(:,1:5)

因此,您可以用

替换parfor循环
P = zeros(301,5,numel(R),numel(C));
for ij = 1 : numel(CGrid)
    c2 = [A; B; CGrid(ij); D; RGrid(ij)];
    [t,c] = ode45('ode_sys',0:300,c2);
    c = max(c,0);
    P(:,:,ij) = c(:,1:5);
    parsave('data.mat',P);
end