Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/performance/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Algorithm Octave/Matlab-迭代内存中的平凡/不可能算法挑战_Algorithm_Performance_Matlab_Octave_Vectorization - Fatal编程技术网

Algorithm Octave/Matlab-迭代内存中的平凡/不可能算法挑战

Algorithm Octave/Matlab-迭代内存中的平凡/不可能算法挑战,algorithm,performance,matlab,octave,vectorization,Algorithm,Performance,Matlab,Octave,Vectorization,存在一个输入向量,该向量具有允许的值集{-2,-1,0,1,2},例如 input = [2 2 2 2 0 1 0 -1 0 -2 -2 -1 0 1] 从开始到结束迭代地扫描向量,在每个点上,基于向量的当前值和之前迭代确定的某个累积值,实现特定的转换表。该值通过请求的步骤(此处为3)递增/递减,直至其不能超过的最大值(此处为9)。 输出向量表示根据定义的转换从当前输入值和累积中导出的某些正在进行的增量 倍频程(3.8)中的循环性能非常差,我找不到一种方法来矢量化它。当在输入和输出之间使用这

存在一个输入向量,该向量具有允许的值集
{-2,-1,0,1,2}
,例如

input = [2 2 2 2 0 1 0 -1 0 -2 -2 -1 0 1]
从开始到结束迭代地扫描向量,在每个点上,基于向量的当前值和之前迭代确定的某个累积值,实现特定的转换表。该值通过请求的步骤(此处为3)递增/递减,直至其不能超过的最大值(此处为9)。 输出向量表示根据定义的转换从当前输入值和累积中导出的某些正在进行的增量

倍频程(3.8)中的循环性能非常差,我找不到一种方法来矢量化它。当在输入和输出之间使用这种间接的累积记忆时,矢量化是可能的吗

input = [2 2 2 2 0 1 0 -1 0 -2 -2 -1 0 1] 
step  = 3;
top   = 9;
acc = out = 0;

for i = 1 : length(input) 
  if     (input(i) == +2) 
          if (acc <         0) out(i) = -acc+step; 
      elseif (acc >  top-step) out(i) = 0; 
      elseif (acc >=        0) out(i) = step; 
       endif 
  elseif (input(i) == +1) 
          if (acc >=        0) out(i) = 0; 
      elseif (acc <         0) out(i) = -acc; 
       endif 
  elseif (input(i) ==  0)      out(i) = 0; 
  elseif (input(i) == -1) 
          if (acc <=        0) out(i) = 0; 
      elseif (acc >         0) out(i) = -acc; 
       endif 
  elseif (input(i) == -2) 
          if (acc >         0) out(i) = -acc-step; 
      elseif (acc < -top+step) out(i) = 0; 
      elseif (acc <=        0) out(i) = -step; 
       endif 
  endif 
  acc += out(i);
endfor
out

out =
3 3 3 0 0 0 0 -9 0 -3 -3 0 0 6
# e.g. the -9 resets the first three 3's buildup: 3+3+3-9=0

为什么循环速度慢的一个大问题是,没有为
输出
向量预先分配内存,除此之外,因为逻辑依赖于先前的处理,所以向量化要稍微多一些complicated@MZimmerman6和Oleg thx的提示,你是对的,虽然它没有帮助太多(
8.95/9.37~=5%
).我实际上是在目标程序中做的,忘记了在本例中使用它。将更新now@Pawel请记住,您正在进行280000次迭代。由于MATLAB/Octave是一种解释语言,这可能会相当缓慢。如果您确实需要提高速度,请尝试使用编译后的语言编写函数,并在从Octave/MATLAB中调用它。这将大大提高速度。@MZimmerman6是的,这将是我的第二个最佳选择-用C重写它,那时肯定会非常快。我希望这可以避免,并保持为矢量化的Octave,这从开发人员/开发人员的角度来看更方便。今天我已经发布了我认为另一个算法是不可行的,答案是惊人的干净和快速:。希望这个问题也存在这样的算法。我必须承认这是一个有趣的算法。关键是要确定一系列可以将acc创建为向量的步骤。向量化作业通常是消除那些临时保留变量,或者在一个时间内创建它们步骤-2+2部分并没有那么难,因为cumsum可以用来找到它们所需的阶跃贡献,max()和min()可以用来将它们夹在+/-顶部。abs(min(0,acc))或与max相同的值可以得到-1+1部分的意图……也许abs(min(0,sign(acc)))将得到一个用于符号翻转的乘法向量…然后使用选择性赋值进行查找…嗯。。。
input = repmat([2 2 2 2 0 1 0 -1 0 -2 -2 -1 0 1], 1,20000);
out   = zeros(1, length(input));
tic; for i = 1 : length(input) 
  (...)
endfor; toc;
Elapsed time is 8.95053 seconds.