插值并替换零

时间:2015-06-07 20:15:32

标签: matlab linear-interpolation

我在MATLAB中有3 x nn是随机数)矩阵。 n=13的示例:

M = [40, 0, 0, 0, 41, 0, 0, 0, 0, 0, 41.6, 0, 20;
     20, 0, 0, 0, 23, 0, 0, 0, 0, 0, 23, 0, 189;
     102, 0, 0, 0, 192, 0, 0, 0, 0, 0, 96, 0, 21];

每行中两个非零数字之间的零个数是随机的,但这个数字在行之间总是相同的。我想像这样插入每一行:

Minter = [40, 40.25, 40.5, 40.75, 41, 41.1, 41.2, 41.3, 41.4, 41.5, 41.6, 30.8, 20;
          20, 20.75, 21.5, 22.25, 23, 23,   23,   23,   23,   23,   23,   106, 189;
          102, 124.5, 147, 169.5, 192, 176, 160,  144,  128,  112,  96,   58.5, 21];

所以我想用用线性插值方法得到的数字替换零。

我写了自己的功能来做到这一点。我正在使用MATLAB函数find来搜索>0的数字索引,然后根据两个索引之间的差异(来自find函数)并依赖于第一个左右非零数字(来自原始矩阵),我计算这两个非零数字之间的数字,并用原始矩阵中的这些数字替换零。我正在分别处理每一行。

这种方法工作正常,但速度不是很快。在MATLAB中有更快的方法吗?我尝试了interp1功能,但没有取得多大成功。

1 个答案:

答案 0 :(得分:3)

是的,你仍然可以使用interp1,但你必须聪明一点。注意到你分别插入矩阵的每一行这一事实,我们可以使用find,我们可以对矩阵的转置进行操作,以找到那些列主要位置不为零。这很重要,因为我们想要插入每行的矩阵值,find按列主要顺序工作。如果要每行操作,则需要转置矩阵以获得所需的效果。

完成后,您可以使用这些索引以及矩阵转置中非空的关键点中的那些值,然后使用从1到尽可能多的元素的查找点。在M中填写M中为零的值。这只会给我们一个1D数组,所以我们需要reshape矩阵并在完成后转置回来。转置也很重要,因为reshape以列为主的方式重塑了一个向量,所以最后一步确保我们得到行主要的所有内容。

做这样的事情:

%// Your matrix
M=[40, 0, 0, 0, 41, 0, 0, 0, 0, 0, 41.6, 0, 20;
20, 0, 0, 0, 23, 0, 0, 0, 0, 0, 23, 0, 189;
102, 0, 0, 0, 192, 0, 0, 0, 0, 0, 96, 0, 21];

%// New code
Mt = M.'; %// Transpose
ind = find(Mt); %// Find column-major indices
Minter = interp1(ind, Mt(ind), 1:numel(M)); %// Interpolate per row
Minter = reshape(Minter, size(M,2), size(M,1)).'; %// Reshape and transpose back

我们得到:

Minter =

  Columns 1 through 8

   40.0000   40.2500   40.5000   40.7500   41.0000   41.1000   41.2000   41.3000
   20.0000   20.7500   21.5000   22.2500   23.0000   23.0000   23.0000   23.0000
  102.0000  124.5000  147.0000  169.5000  192.0000  176.0000  160.0000  144.0000

  Columns 9 through 13

   41.4000   41.5000   41.6000   30.8000   20.0000
   23.0000   23.0000   23.0000  106.0000  189.0000
  128.0000  112.0000   96.0000   58.5000   21.0000

这与您想要的输出一致。