我不能自己删除这个循环,如果有人可以帮我优化这段代码 - 欢迎。
M = length(w);
expt = exp(-t .* (phis * w'));
G = zeros(M, M);
for i = 1 : M
for j = 1 : M
last = 2 * reg_coef * eye(M);
G(i,j) = last(i, j) + mean(expt .* t .^2 .* phis(:,i) .* phis(:,j) ./ (1 + expt) .^ 2);
end
end
答案 0 :(得分:3)
只需编写更清晰的代码,您就可以做得更好 - 确保正确分配,确保从循环中删除重复的计算等:
编辑:您还可以看到生成的矩阵G
是对称的,因此您只需计算上三角形并在后面填充下三角形作为转置即可立即获得2x
加速
至少在我的MATLAB
时,通过使用临时数组将调用向量化mean()
来实现另一个大的加速。
N = 100;
M = 100;
w = rand(1,M);
t = rand(N,1);
phis = rand(N,M);
reg_coeff = rand(1,1);
expt = exp(-t .* (phis * w'));
%% Initial version
tic
for i = 1 : M
for j = 1 : M
last = 2 * reg_coeff * eye(M,M);
G1(i,j) = last(i,j) + mean(expt .* t .^ 2 .* phis(:,i) .* phis(:,j) ./ (1 + expt) .^ 2);
end
end
t1 = toc;
%% Faster version
tic
coeff = expt .* t .^ 2 ./ (1 + expt) .^ 2;
G2 = zeros(M,M);
TT = zeros(M,M);
for i = 1 : M
for j = i : M % only form upper triangle
TT(:,j) = coeff .* phis(:,i) .* phis(:,j);
end
G2(i,i:M) = mean(TT(:,i:M),1); % vectorise call to mean()
end
G2 = 2 * reg_coeff * eye(M,M) + G2 + triu(G2,+1)';
t2 = toc;
%% Compare versions
speed = t1/t2
error = max(max(abs(G2 - G1)))
对于100x100
这种情况,我的机器上的加速速度大约为41.0
。
希望这有帮助。
答案 1 :(得分:2)
至少,你可以从循环中取出很多术语:
last = 2 * reg_coef * eye(M);
A = expt .* t .^2;
B = (1 + expt) .^ 2;
for i = 1 : M
X = A .* phis(:,i) ./ B;
for j = 1 : M
G(i,j) = mean(X .* phis(:,j));
end
end
G = G + last;