简体   繁体   中英

MATLAB: summing values in matrix up to a threshold level of one column

So, I have a matrix with 2 columns and 5 rows (as an example).

2 1
5 1
3 1
4 1
7 1

what I want to do is:

Starting from position (1,1) and moving down the first column, find the cells that lead to a value <10. In this case I would have:

step 1: 2 = 10? No, continue
step 2: 2+5 = 10? No, continue
step 3: 2+5+3 = 10? Yes, stop and return the sum of the corresponding values in the second column
step 4: 4 = 10? No, continue
step 5: 4+7 = 10? No, it's larger, thus we save the previous step and return 1 form the second column.

In the end of this process I would need to obtain a new matrix that looks like this:

10 3
4 1
7 1

You can perform exactly the logic you described in a loop.

  • Each row, test the "recent sum", where "recent" here means from the last output row to the current row.

  • If the sum is 10 or more, add to the output as described. Otherwise continue to the next row.

Code:

% Original data
x =[2 1; 5 1; 3 1; 4 1; 7 1];
% Output for result
output = [];
% idx is the row we start sum from on each test
idx = 1;
% Loop over all rows
for ii = 1:size(x,1)
    % Get sum in column 1
    s = sum(x(idx:ii, 1));
    if s == 10
        % Append row with sums
        output = [output; 10 sum(x(idx:ii,2))];
        idx = ii+1;
    elseif s > 10
        % Append all "recent" rows
        output = [output; x(idx:ii,:)];
        idx = ii+1;
    end
end

Result:

>> disp(output)
   10  3
    4  1
    7  1

This is my proposed solution:

% Create A and the cumulative sum of its first column...
A = [2 1; 5 1; 3 1; 4 1; 7 1];
A_cs = cumsum(A(:,1));

% Create a variable R to store the result and an indexer to it...
R = NaN(size(A_cs,1),2);
R_off = 1;

% Perform the computation...
while (~isempty(A_cs))
    idx = find(A_cs <= 10);
    idx_max = max(idx);

    R(R_off,:) = [A_cs(idx_max) sum(A(idx,2))];

    A_cs = A_cs - A_cs(idx_max);
    disp(A_cs);
    A_cs(idx) = [];

    R_off = R_off + 1;
end

% Clear unused slots in R...
R(any(isnan(R),2),:) = [];

The computation is performed by taking the maximum index of the first cumsum group that lies within the specified threshold ( 10 in this case). Once it has been found, its corresponding value is inserted into the result matrix and the cumsum array is updated by removing the group entries and subtracting their sum. When the cumsum array is empty, the iteration finishes and R contains the desired result.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM