【问题标题】:Matrix row/column manipulation in matlabmatlab中的矩阵行/列操作
【发布时间】:2016-12-21 19:53:34
【问题描述】:

我有以下函数用于分散矩阵中 1 的数量,如果存在全 0 或全 1 的行,则必须删除该特定行

function ReducedMatrix = ReduceMatrix(result)
D1 = sum(result(:));
NumberOfOnes = floor(D1*0.3);
NewMatrix = zeros(size(result));
NewMatrix(randi(numel(NewMatrix),1,NumberOfOnes)) = 1;
ReducedMatrix = NewMatrix;
while numel(ReducedMatrix)/numel(NewMatrix) > 0.2
IndexOfFullRows = find(all(ReducedMatrix));
if isempty(IndexOfFullRows)

    break
end
ReducedMatrix(:,IndexOfFullRows(1)) = [];

end
end

函数的输入和输出如下

 result =

 0     1     1     1     1     1     1     1     1     1
 1     1     1     1     1     0     1     0     1     1
 1     1     0     1     1     1     1     1     1     1
 1     1     1     1     1     1     1     1     1     0
 1     1     1     1     1     1     0     1     0     1
 1     0     1     1     1     1     1     0     1     1
 1     1     1     1     0     1     1     1     0     1
 1     0     1     1     1     0     1     1     1     1
 1     1     1     1     0     1     0     1     1     1
 1     1     1     0     1     1     1     1     1     1


 ReducedMatrix =

 0     1     1     0     0     0     0     0     1     0
 0     1     0     0     0     0     0     1     0     0
 1     1     1     0     0     0     0     0     0     0
 0     0     0     1     0     0     1     0     0     0
 0     0     0     0     0     0     1     0     0     0
 0     1     0     0     0     0     1     0     1     1
 1     0     1     0     0     0     0     0     0     0
 0     0     0     0     0     0     0     1     0     1
 0     0     0     0     0     0     0     0     0     0
 1     0     1     0     0     0     0     0     0     1


row_sum =

 3
 2
 3
 2
 1
 4
 2
 2
 0
 3


col_sum =

 3     4     4     1     0     0     3     2     2     3

现在,如果存在 row_sum/col_sum 等于 0 或 1 的行或列,则必须删除相应的行。 例如。 Row-R4,R9 和 Col-C4,C5,C6 的 row_sum 和 col_sum 为 1,0。所以将它们加起来 R4,R9,C4,C5,C6 = 5 行必须从矩阵中消除,所以我的简化矩阵的大小应该是 5x5。请注意,不应删除列,而不是删除具有 0 和 1 的列,而是可以删除相应的行。同样,此函数必须针对具有相同约束的较大矩阵运行。我尝试执行上述功能,但是我没有足够的技能来达到我想要的结果,非常感谢任何帮助

【问题讨论】:

  • 那么,如果现在删除一行会改变列总和并使其现在必须删除另一列,会发生什么?
  • 我在函数中做了一个限制,不能超过 30% 的行可以减少

标签: matlab networking matrix


【解决方案1】:

我发现您的代码存在许多潜在问题和可能的简化。

一方面,您构造原始矩阵的方式NewMatrix(randi(numel(NewMatrix),1,NumberOfOnes)) = 1; 的行为可能与您预期的不同。 randi 不保证相同的索引不会在输出中多次出现,因此您的新矩阵可能比原来的矩阵少。要解决这个问题,请使用randperm 打乱元素:

ReducedMatrix = [ones(1, NumberOfOnes), zeros(1, numel(result) - NumberOfOnes)];
ReducedMatrix = ReducedMatrix(randperm(numel(ReducedMatrix)));
ReducedMatrix = reshape(ReducedMatrix, size(result));

其次,您不需要将新矩阵构造为NewMatrix,然后将其重新分配为ReducedMatrix = NewMatrix;。只需执行ReducedMatrix = zeros(size(result)); 并跳过重新分配。对于while 循环条件,其中NewMatrix 似乎已“使用”,请记住numel(NewMatrix) == numel(result)

如果您不删除同类列,仅删除行,则不需要循环来执行删除:

rowSum = sum(ReducedMatrix, 2);
rowMask = (rowSum == size(ReducedMatrix, 2) | rowSum == 0);
ReducedMatrix(rowMask, :) = [];

删除行时,您的原始代码似乎交换了行索引和列索引。它也没有处理全零的情况。如果要删除不超过 30% 的行,可以在删除之前执行以下操作:

rowMask = find(rowMask); % Convert to indices
rowMask = rowMask(1:min(numel(rowMask), round(0.3 * size(ReducedMatrix, 2))));

【讨论】:

  • 感谢您的回答,我尝试您的解决方案如何在没有 Randi 的情况下构建我的原始矩阵
  • @CJs 更新答案。
  • 我收到以下错误 - || 的操作数和 && 运算符必须可转换为逻辑标量值。 ReduceMatrix1 中的错误(第 19 行) rowMask = (rowSum == size(ReducedMatrix, 2) || rowSum == 0);
  • 修正错字,应该是一个管道。
  • 我得到一个空矩阵,我没有按照你的建议使用任何循环。这就是我所做的ReducedMatrix = [ones(1, NumberOfOnes), zeros(1, numel(result) - NumberOfOnes)]; ReducedMatrix = ReducedMatrix(randperm(numel(ReducedMatrix))); ReducedMatrix = reshape(ReducedMatrix, size(result)); ReducedMatrix = zeros(size(result)); rowSum = sum(ReducedMatrix, 2); rowMask = (rowSum == size(ReducedMatrix, 2) | rowSum == 0); ReducedMatrix(rowMask, :) = []; rowMask = find(rowMask); % Convert to indices rowMask = rowMask(1:min(numel(rowMask), round(0.3 * size(ReducedMatrix, 2)))); end
猜你喜欢
  • 1970-01-01
  • 2015-06-11
  • 2023-03-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-09-26
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多