【问题标题】:Removing four nested loops in Matlab在 Matlab 中删除四个嵌套循环
【发布时间】:2014-07-25 05:07:03
【问题描述】:

我在 Matlab 中有以下四个嵌套循环:

timesteps = 5;
inputsize = 10;
additionalinputsize = 3;
outputsize = 7;

input = randn(timesteps, inputsize);
additionalinput = randn(timesteps, additionalinputsize);
factor = randn(inputsize, additionalinputsize, outputsize);

output = zeros(timesteps,outputsize);
for t=1:timesteps
    for i=1:inputsize
        for o=1:outputsize
            for a=1:additionalinputsize
                output(t,o) = output(t,o) + factor(i,a,o) * input(t,i) * additionalinput(t,a);
            end
        end
    end
end

共有三个向量:一个输入向量、一个附加输入向量和一个输出向量。所有这些都是由因素联系在一起的。每个向量都有给定时间步长的值。我需要每个给定时间步的所有组合输入、附加输入和因素的总和。稍后,我需要从输出到输入进行计算:

result2 = zeros(timesteps,inputsize);
for t=1:timesteps
    for i=1:inputsize
        for o=1:outputsize
            for a=1:additionalinputsize
                result2(t,i) = result2(t,i) + factor(i,a,o) * output(t,o) * additionalinput(t,a);
            end
        end
    end
end

在第三种情况下,我需要每个时间步长上所有三个向量的乘积:

product = zeros(inputsize,additionalinputsize,outputsize)
for t=1:timesteps
    for i=1:inputsize
        for o=1:outputsize
            for a=1:additionalinputsize
                product(i,a,o) = product(i,a,o) + input(t,i) * output(t,o) * additionalinput(t,a);
            end
        end
    end
end

这两个代码 sn-ps 可以工作,但速度非常慢。如何删除嵌套循环?

编辑:添加了值并更改了一些小东西,因此 sn-ps 是可执行的

Edit2:添加了其他用例

【问题讨论】:

  • 这个问题不是关于统计的,可能不适合这个论坛。
  • 请包括一个最小的例子。定义所有变量,以便我们可以运行代码
  • 您是否打算保存循环内部的值,因为您目前不在

标签: arrays performance matlab multidimensional-array vectorization


【解决方案1】:

第一部分

一种方法 -

t1 = bsxfun(@times,additionalinput,permute(input,[1 3 2]));
t2 = bsxfun(@times,t1,permute(factor,[4 2 1 3]));
t3 = permute(t2,[2 3 1 4]);
output = squeeze(sum(sum(t3)));

或避免使用squeeze 的轻微变体-

t1 = bsxfun(@times,additionalinput,permute(input,[1 3 2]));
t2 = bsxfun(@times,t1,permute(factor,[4 2 1 3]));
t3 = permute(t2,[1 4 2 3]);
output = sum(sum(t3,3),4); 

第二部分

t11 = bsxfun(@times,additionalinput,permute(output,[1 3 2]));
t22 = bsxfun(@times,permute(t11,[1 4 2 3]),permute(factor,[4 1 2 3]));
result2=sum(sum(t22,3),4);

第三部分

t11 = bsxfun(@times,permute(output,[4 3 2 1]),permute(additionalinput,[4 2 3 1]));
t22 = bsxfun(@times,permute(input,[2 4 3 1]),t11);
product = sum(t22,4);

【讨论】:

  • 效果很好!你能帮我解决我刚刚添加的第三个用例吗?
  • @user1406177 也为此添加了解决方案。
  • 很好的答案。很高兴看到 bsxfun 在行动。
  • @FredS 让bsxfun 探索是个大问题!谢谢顺便说一句:)
  • @user1406177 t11 = bsxfun(@times,additionalinput,permute(factor,[4 2 1 3])); t22 = bsxfun(@times,t11,permute(output,[1 3 4 2])); result2 = squeeze(sum(sum(t22,2),4));
猜你喜欢
  • 1970-01-01
  • 2017-06-20
  • 1970-01-01
  • 1970-01-01
  • 2014-05-03
  • 1970-01-01
  • 2016-03-17
  • 2014-06-10
  • 1970-01-01
相关资源
最近更新 更多