Image Compression Using the Singular Value Decomposition (SVD) with MATLAB I'm new to both linear algebra and MATLAB.
I need help with this code with the objective of compressing image using the Singular Value Decomposition (SVD).
The code is currently working, if I run with e.g sigma_threshold = 10, I get a blurry picture, if I set it to 100 it's even more blurry etc.

I have searched all over the web and found a lot of similiar examples that I have used to improve this code with, but still I know I can do it a lot more elegant.

One problem is that I dont fully understand the math behind what I'm doing, and thus I don't know really know what to do, particularly with the matrices U and V in [U S V] = svd(A).

Wondered if someone could give me a hint how to improve the sections under the comments 
"%Find the first index smaller than sigma_threshold" and "%Compose the red, green and blue channel again until the sigma value"

function svd_exercise(imagename,sigma_threshold)

image = imread(imagename); 
image = im2double(image);

%Decompose the image in rgb values
R = image(:, :, 1);
G = image(:, :, 2);
B = image(:, :, 3);

%Compute the Single Value decomposition for each channel
[U_R, S_R, V_R] = svd(R);
[U_G, S_G, V_G] = svd(G);
[U_B, S_B, V_B] = svd(B);

%Find the first index smaller than sigma_threshold
[red_j, ~] = find(S_R &gt; 0 &amp; S_R &lt; sigma_threshold, 1);
[green_j, ~] = find(S_G &gt; 0 &amp; S_G &lt; sigma_threshold, 1);
[blue_j, ~] = find(S_B &gt; 0 &amp; S_B &lt; sigma_threshold, 1);

%Compose the red, green and blue channel again until the sigma value
R_K = U_R(:, 1:red_j) * S_R(1:red_j, 1:red_j) * V_R(:, 1:red_j)';
G_K = U_G(:, 1:green_j) * S_G(1:green_j, 1:green_j) * V_G(:, 1:green_j)';
B_K = U_B(:, 1:blue_j) * S_B(1:blue_j, 1:blue_j) * V_B(:, 1:blue_j)';

AK = zeros(size(image));
AK(:,:,1) = R_K;
AK(:,:,2) = G_K;
AK(:,:,3) = B_K;
If you look at the structure of your matrices of singular values S_R, S_G and S_B, you'll see that the non-zero entries lie on the diagonal. You can check only these entries by using diag, removing the need for your S_R&gt;0 condition.

This also means that for find you don't need to supply the second output argument.

To get the first non-zero entries less than sigma_threshold you can hence use

red_j = find(diag(S_R) &lt; sigma_threshold, 1);
green_j = find(diag(S_G) &lt; sigma_threshold, 1);
blue_j = find(diag(S_B) &lt; sigma_threshold, 1);


Bear in mind that this is the first value which should be cut off, not the last value to include, hence you might want to do

red_j = find(diag(S_R) &lt; sigma_threshold, 1) - 1;


or

red_j = find(diag(S_R) &gt;= sigma_threshold, 1, 'last');