我目前正在尝试使用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
答案 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