필터 지우기
필터 지우기

I have a matrix given below. I want to count the number of sets of consecutive non zero values along each row. Detailed description and desired result given below

조회 수: 10 (최근 30일)
A = [0 0 3 4 1 0 7 8;
6 0 0 4 5 1 0 0]
In the first row there are 2 sets of consecutive non zero values i.e. First set of nonzero consecutive is (3 4 1) and second set of non zero consecutive values is (7 8). In the second row there is only one set of non zero consecutive values, that is (4 5 1).
desired_set_of_non_zero_consecutive_values=[2;1]

채택된 답변

John D'Errico
John D'Errico 2023년 7월 1일
편집: John D'Errico 2023년 7월 1일
These problems are always simpler, IF you reduce it to simpler sub-tasks. And, I'm sure there are simpler ways to solve this problem. But what I'm doing in this answer is to show you how you might think through a problem, not so much find the very simplest scheme to solve the problem. Arguably, that would just involve a loop.
You need to remember your target, and then find ways to get closer and closer to that goal.
It looks like singleton elements that are not consecutive non-zeros don't count. And I'll add a few rows to make it interesting, making sure we can resolve all issues.
A = [0 0 3 4 1 0 7 8;
6 0 0 4 5 1 0 0;
1 2 3 0 1 2 0 1;
0 0 0 1 2 3 4 0;
0 0 0 0 1 0 0 0;
0 0 0 0 0 0 0 0];
First, turn this into a boolean matrix. All we care about are the non-zeros.
Ahat = A ~= 0
Ahat = 6×8 logical array
0 0 1 1 1 0 1 1 1 0 0 1 1 1 0 0 1 1 1 0 1 1 0 1 0 0 0 1 1 1 1 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0
Next, I'll pad a spare zero at the beginning and the end of each row. This will make it easier to find the strings of non-zeros, and also to kill off those pesky singletons.
nr = size(A,1);
Ahat = [false(nr,1),Ahat,false(nr,1)]
Ahat = 6×10 logical array
0 0 0 1 1 1 0 1 1 0 0 1 0 0 1 1 1 0 0 0 0 1 1 1 0 1 1 0 1 0 0 0 0 0 1 1 1 1 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0
Next, we want to kill off those singleton elements in any row. Surely many ways to do this. But I'll pick a simple one.
Amask = conv2(Ahat,[1 2 4],'valid') ~= 2
Amask = 6×8 logical array
1 1 1 1 1 1 1 1 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 0 1 1 1 1 1 1 1 1 1 1 1 1 0 1 1 1 1 1 1 1 1 1 1 1
Ahat(:,2:end-1) = Ahat(:,2:end-1).*Amask
Ahat = 6×10 logical array
0 0 0 1 1 1 0 1 1 0 0 0 0 0 1 1 1 0 0 0 0 1 1 1 0 1 1 0 0 0 0 0 0 0 1 1 1 1 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
So EVERY consecutive block of non-zeros is in there, but only the ones longer than 1 element. And every one of those blocks ends with the sub-string [1 0]. So all we need to do now is count the number of times we find the sub-string [1 0] in each row. Again, break larger problems down into simpler ones.
loc = strfind(string(char(Ahat + '0')),"10")
loc = 6×1 cell array
{[ 6 9]} {[ 7]} {[ 4 7]} {[ 8]} {0×0 double} {0×0 double}
That line looks to be a kludge, but it works, and I'm not going to spend any mental energy to make it shorter. Nice though. It gives me a cell array containing the locations of the end points of all consecutive sub-strings. All we need to do now is to count the number of elements in each entry of that cell array.
desired_set_of_non_zero_consecutive_values = cellfun(@numel,loc)
desired_set_of_non_zero_consecutive_values = 6×1
2 1 2 1 0 0
It actually is not that large a set of steps I went through, though I think, since I left off the semi-colons, and spent a lot of time talking through the problem, it probably seems a lengthy solution. But the point is to teach how to tackle a problem like this.
Break big problems down into small ones. Eat programming elephants one byte at a time.

추가 답변 (1개)

sp6038sy
sp6038sy 2023년 7월 1일
편집: sp6038sy 2023년 7월 1일
Another approach —
I tried to find the number of continuous data by finding the start and end points of the continuous data.
A = [0 0 3 4 1 0 7 8;
6 0 0 4 5 1 0 0];
desired_set_of_non_zero_consecutive_values = zeros(height(A), 1);
padA = padarray(A, [0,1]);
binMap = padA ~= 0;
for i = 1:height(padA)
len = find(-1 == diff(binMap(i, :))) - find(1 == diff(binMap(i, :)));
desired_set_of_non_zero_consecutive_values(i) = sum(len >= 2);
end
disp(desired_set_of_non_zero_consecutive_values);
2 1

카테고리

Help CenterFile Exchange에서 Array and Matrix Mathematics에 대해 자세히 알아보기

태그

제품

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by