2 views (last 30 days)

function [Q, R] = grams(A)

[m, n] = size(A);

Q = zeros(m,n);

Asave = A;

if norm(A(:,1)) < sqrt(eps)

error('The first Column of A is zero vector')

end

Q(:,1) = A(:,1)/norm(A(:,1));

for j = 2:n

for k = 1:j-1

mult = (A(:, j)'*Q(:, k)) / (Q(:, k)'*Q(:, k));

A(:, j) = A(:, j) - mult*Q(:, k);

end

%if norm(A(:, j)) < sqrt(eps)

%error('Columns of A are linearly dependent.')

%end

Q(:, j) = A(:, j) / norm(A(:, j));

end

%if norm(Q'(:,n)) <sqrt(eps)

%B = zeros(m, n-1);

%B(:,1:n-1) = Q'(:,1:n-1);

%end

R = Q'*Asave;

for i = 2:n

if norm(R(:,i))<sqrt(eps)

R (:,i) = [];

end

end

Mohammad Sami
on 13 Oct 2020

Edited: Mohammad Sami
on 13 Oct 2020

The issue is in the if statements. You are doing a vector comparison, which will return a logical vector. If statement requires a scalar value. To convert it to a logical scalar use function all or any.

For example

if true

if all(norm(A(:,1)) < sqrt(eps))

error('The first Column of A is zero vector')

end

%%%%%%%other code

if all(norm(R(:,i))<sqrt(eps))

R (:,i) = [];

end

end

Walter Roberson
on 14 Oct 2020

If statement requires a scalar value.

That is not correct.

if and while are considered true if all the elements to be tested are non-zero. To put that another way, they are considered false if even one element being tested is 0. false is 0.

Effectively, if and while have a built-in all()

However, testing a non-scalar is often a sign that the programmer did not realize that a non-scalar was possible at that point, so it is often a sign that the code will not work as intended for non-scalar values.

Sometimes, programmers who are aware that the test is effectively all(), will rely upon that behavior, knowing that non-scalars are possible at that point in the code. That kind of code is permitted, but it is not recommended: code that explicitly uses all() or any() is much much more readable to other people.

Image Analyst
on 13 Oct 2020

To get rid of columns with a nan anywhere in the column, you can do this:

% Create sample data with some nans in there.

A = magic(9);

A(2,3) = nan;

A(3,5) = nan;

A(6,7) = nan

goodColumns = ~any(isnan(A), 1) % Columns without nan in any of the rows.

AGood = A(:, goodColumns)

Of course you can assign it back to A instead of AGood if you want to replace the original A.

You'll see:

A =

47 58 69 80 1 12 23 34 45

57 68 NaN 9 11 22 33 44 46

67 78 8 10 NaN 32 43 54 56

77 7 18 20 31 42 53 55 66

6 17 19 30 41 52 63 65 76

16 27 29 40 51 62 NaN 75 5

26 28 39 50 61 72 74 4 15

36 38 49 60 71 73 3 14 25

37 48 59 70 81 2 13 24 35

goodColumns =

1×9 logical array

1 1 0 1 0 1 0 1 1

AGood =

47 58 80 12 34 45

57 68 9 22 44 46

67 78 10 32 54 56

77 7 20 42 55 66

6 17 30 52 65 76

16 27 40 62 75 5

26 28 50 72 4 15

36 38 60 73 14 25

37 48 70 2 24 35

Image Analyst
on 13 Oct 2020

Image Analyst
on 14 Oct 2020

Jingyi, you still forgot to attach your data like I directly asked for. What are you passing in for A?

Why should I expect any column of R to have a nan in it? I imagine it won't always have nans in them. It might have nans in them only for certain A matrices. So what A did you pass in that gave a nan in R?

And you compute AGood but don't do anything with it. You return Q and R. Do you want R to be the good columns of R, like

R = R(:, goodColumns); % Instead of AGood.

Opportunities for recent engineering grads.

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

Start Hunting!
## 0 Comments

Sign in to comment.