1 view (last 30 days)

For this problem the objective was:

Write a function that receives matrix A (e.g. 4x4 integer matrix) and returns the matrix B and value b. The value b should be the sum of all matrix elements of matrix A. For matrix B and value b the following two rules should be followed: • The matrix B should have only the second and third rows of matrix A; unless matrix A has less than 3 rows; in this case,an error message (”Err1: Matrix Size Incompatible”) should be returned for B and b should be -1. • The matrix B should have only the fist and second columns of matrix A, unless matrix A has less than 2 columns; in this case, an error message (”Err1: Matrix Size Incompatible”) should be returned for B and b should be -1.

My code is the following, and I am just wondering if there is a better way to go about doing what I did here either more efficiently or just more clearly?

function [B,b] = shrink(A)

% function to shrink A down to a 2x2 integer and return the sum as value b

B = A;

% sets B array equal to A.

[rowsInB, columnsInB] = size(B);

% finds number of rows and columns in B

msg1 = 'Err1: Matrix Size Incompatible';

% defines a msg for errors given later

if rowsInB < 3

% defines a case if the rows is less than 3 to return error message

% and value of -1 for b

b = -1;

B = msg1;

return

else

%if first case is not met, remove the 1st row of the array

B(1,:) = [];

end

[rowsInB,~] = size(B);

% gets new row size

for rows = 3:rowsInB

% deletes any rows past 2

B(rowsInB,:) = [];

[rowsInB,~] = size(B);

end

if columnsInB < 2

% defines a case if the columns is less than 2 to return error message

% and value of -1 for b

b = -1;

B = msg1;

return

end

[~,columnsInB] = size(B);

% gets new column size for B

for columns = 3:columnsInB

B(:,columnsInB) = [];

[~,columnsInB] = size(B);

end

b = sum(A,'all');

% gets the sum of all elements in the original array

end

Sindar
on 6 Oct 2020

generally, deleting columns (esp. one-by-one) is less efficient than indexing. Assuming all of the tests have passed, you can simply build B as the 2nd-3rd row and 1st-2nd column of A like this:

B = A(2:3,1:2);

Sindar
on 6 Oct 2020

in cases where deletion is easier, you can delete multiple columns (or multiple rows) at the same time:

For example, delete all rows after the 4th:

B(5:end,:) = [];

note that this will work even when B has fewer than 5 rows. For example, a 3-row B will expand this to

B(5:3,:) = [];

and 5:3 is an empty array, so nothing is deleted

Sindar
on 6 Oct 2020

Definitely! I've learned a lot just reading answers to others questions. If you want a fuller intro, the Onramp is great, and this is the indexing reference I use.

One particular tip: Matlab is designed so that relatively little requires a loop - many actions can be done more efficiently without. Personally, I find "can I do this without a loop?" questions interesting (and/or very easy) and I get the impression some of the Answers MVPs do as well, so ask away.

Final note: when asking questions, please put code in code blocks (see the toolstrip) and try to write more specific question titles (e.g., "how do I efficiently extract rows and columns?") and tags ("loop", "extract columns", "speedup", something like that). I know it's not always clear when writing a question what aspects are most relevant to the answerers, but just something to keep in mind

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

Start Hunting!
## 0 Comments

Sign in to comment.