如何减少Matlab'find'函数的内存需求?

时间:2010-11-11 04:49:10

标签: matlab

我在Matlab中有一行代码:

  output = find(input);

其中列向量“output”包含列向量“input”中其元素非零的所有索引。例如,如果:

 input = [1 3 4 0 0 2 0];

然后结果,output = find(输入);将是:

 output = 
     1
     2
     3
     6

对应于非零的数组“输入”的第1(“1”),第2(“3”),第3(“4”)和第6(“2”)索引。

由于我的“输入”数组非常大,这行代码消耗了我所有的本地RAM以及大量的虚拟内存,导致系统慢慢爬行。

任何人都知道减少这种操作的内存需求的好方法(或任何方式)?我想把“查找”代码放在一个循环中,但由于数组“输出”的大小(以及这个数组的索引)取决于“查找”操作的结果,我看不出它是如何可能的这样做。出于想法。

提前感谢您的任何意见/建议。 -gkk

2 个答案:

答案 0 :(得分:3)

如果你有比零更多的非零值,也许你可以使用补语,即:output=find(input==0)而不是默认值,相当于output=find(input~=0)

此外,您可以使用逻辑索引,比较:

>> output1 = find(input);
>> output2 = (input~=0);
>> whos output*
  Name         Size            Bytes  Class      Attributes

  output1      1x4                32  double               
  output2      1x7                 7  logical    

注意它是如何存储为“booleans”的向量,每个是一个字节(对于“double”为8个字节)

答案 1 :(得分:2)

如果您有足够的内存来保存与input大小相同的数组,则可以将调用替换为find

output = 1:length(input);
output = output(input~=0);

如果input的元素少于2 ^ 32-1,则可以将其初始化为uint32,从而进一步节省内存。

更好的方法可能是将input数组转换为sparse,如果input包含大量零,则可以节省内存,然后在其上使用find,即

input = sparse(input);
output = find(input);

修改

要分段执行find操作,我会执行以下操作:

nIn = length(input);
blockLength = 100000;
nBlocks = ceil(nIn/blockLength); %# work in chunks of 100k entries
out = cell(nBlocks,1);
for i=1:nBlocks
   out{i} = (i-1)*blockLength+1:i*blockLength; %# assign as your favorite integer format here
   out{i} = out{i}(input(out{i})~=0);
end
out = cat(1,out{:});