【问题标题】:Matlab: Sorting 2D matrix and retaining nodes in triangle groupsMatlab:对二维矩阵进行排序并保留三角形组中的节点
【发布时间】:2019-04-30 10:52:20
【问题描述】:

我正在尝试优化一个 Matlab 脚本(如下),该脚本可以找到二维空间中所有左下三角形的函数值的边界框。代码遍历所有三角形,然后根据功能值按升序对节点进行排序。这似乎效率低下。

有没有什么方法可以在循环之前对函数值进行排序,但仍保留三角形组中的节点?或者其他一些加快速度的聪明方法?

clear;

x = (1:600)';
y = (1:500);
z = 2 * x.^2 + y;

zGrid = linspace(min(z, [], 'all') - 1, max(z, [], 'all') + 1, 200);

for iX = 1:length(x) - 1
    for iY = 1:length(y) - 1
        % Node indices
        xIndices = [iX, iX, iX + 1];
        yIndices = [iY, iY + 1, iY];

        % Node values
        xTmp = x(xIndices);
        yTmp = y(yIndices);
        zTmp = z(sub2ind(size(z), xIndices, yIndices));

        % Node sorted according to z
        [zSorted, indicesSorted] = sort(zTmp);
        xSorted = xTmp(indicesSorted);
        ySorted = yTmp(indicesSorted);

        % Get bounding box on zGrid
        iMin = find(zGrid <= zSorted(1), 1, 'last');
        iMax = find(zGrid(iMin:end) >= zSorted(end), 1, 'first') + (iMin - 1);
    end
end

【问题讨论】:

  • 您可以使用 meshgrid 生成所有索引:[iX,iY] = meshgrid(x(1:end-1),y(1:end-1)) 然后iX = iX(:),iY = iY(:)

标签: matlab sorting matrix-indexing


【解决方案1】:

您可以使用 meshgrid 生成所有索引,然后只需修改代码以获得所需的输出:

x = (1:600).';
y = (1:500);
z = 2 * x.^2 + y;

zGrid = linspace(min(z(:)) - 1, max(z(:)) + 1, 200);
[X,Y] = meshgrid(x(1:end-1),y(1:end-1));
X = X(:);
Y = Y(:);

% Node indices
xIndices = [X, X, X + 1];
yIndices = [Y, Y + 1, Y];

% Node values
xTmp = x(xIndices);
yTmp = y(yIndices);
zTmp = z(sub2ind(size(z), xIndices, yIndices));

% Node sorted according to z
[zSorted, indicesSorted] = sort(zTmp,2);
xSorted = xTmp(indicesSorted+[0:3:(length(X)-1)*3].');
ySorted = yTmp(indicesSorted+[0:3:(length(Y)-1)*3].');

% Get bounding box on zGrid
% I use fliplr to get the last value and not the first one
[~,iMin] = max(fliplr(zGrid <= zSorted(:,1)),[], 2);
iMin = 200-iMin+1; %first to last value conversion
[~,iMax] = max(zGrid(iMin:end) >= zSorted(:,end),[],2);
iMax = iMax + iMin -1;

【讨论】:

  • 太棒了!谢谢!但是为了使iMax 正确,仍然需要早期版本中的iMax = iMax + iMin -1;。现在,我只是转过头来理解它:)
  • 好吧,我不确定(实际上我不确定这段代码发生了什么:p),我回滚到之前的编辑。 [0:3:(length(X)-1)*3] 向量只是在这里为每行累积添加 +3,以便线性索引指向正确的值。
  • 我刚刚意识到xSortedySorted 中的行与我的代码中的对象不对应。 zSortedxTmpyTmp 完全相同。所以,问题似乎在于使用indicesSorted。你知道如何解决它吗?
  • 我认为问题出在三角形节点按行而不是按列分组以及Matlab如何在线性索引中对单元格进行排序。
  • @Fredrik P,是的,您可以简单地转置这两个矩阵:xTmp = x(xIndices).';yTmp = y(yIndices).';,这样线性索引将处于“正确”方向。线性索引是逐列而不是逐行执行的。
猜你喜欢
  • 1970-01-01
  • 2015-09-17
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-07-03
  • 2015-01-31
  • 2020-08-15
相关资源
最近更新 更多