% Resenje koleginice Milice Glumicic mr05151
% Funkcija nalazi sopstvene vrednosti i sopstvene vektore matrice A, Jakobijevom iterativnom
%metodom

function [svrednosti SV]=JacobiMethod(A,eps)
% dimenzija matrice A
n=size(A,1);
%za svaki slucaj provericemo  da li je matrica A simetricna

for i=1:n
    for j=i:n
        if ~(A(i,j)==A(j,i))
    error('Uneta matrica nije simetricna');
        end
    end
end

% Racunamo nedijagonalnu normu matrice A
ndn=0;
for j=1:n-1
 for i=j+1:n
     ndn=ndn+(A(i,j)*A(i,j));
 end
end
     ndn=sqrt(ndn);

% Ako je nedijagonalna norma 0, matrica je dijagonalna, pa
% su joj sopstvene vrednosti vec na dijagonali
if ndn==0
    J=A;
    return
end
%Ubr ce biti matrica sopstvenih vektora
Ubr=eye(n);
while(1)
    % Pronalazimo indekse najveceg po modulu elementa matrice A
    max=A(2,1);
    k=2;
    l=1;
    for j=1:n-1
        for i=j+1:n
            if (max<abs(A(i,j)))
                k=i;
                l=j;
                max=abs(A(i,j));
            end
        end
    end


    % Nalazimo elemente matrice rotacije koja ce da anulira A(k,l)
 % u slucaju kada je tg(2fi)=beskonacno (tj kada je A[kk]-A[ll] < zad. tacnost)

     if abs(A(k,k)-A(l,l))<eps
            if A(k,l)>0
            cosFi=sqrt(2)/2;
            sinFi=sqrt(2)/2;
             else
            cosFi=-sqrt(2)/2;
            sinFi=sqrt(2)/2;
            end
     else
         %inace
    lambda=-A(k,l);
    mi=-(A(l,l)-A(k,k))/-2;
    omega=sign(mi)*lambda/sqrt(lambda^2+mi^2);

    sinFi=omega/sqrt(2*(1+sqrt(1-omega^2)));
    cosFi=sqrt(1-sinFi^2);
      end



    % Gradimo matricu rotacije umetanjem u jedinicnu
    %
    U=eye(n);
    U(k,k)=cosFi;
    U(l,l)=cosFi;
    U(k,l)=-sinFi;
    U(l,k)=sinFi;
   
    Ubr=Ubr*U;

    % Anuliramo najveci po modulu element matrice A
    A=U'*A*U;


    % Racunamo nedijagonalnu normu tekuce matrice
ndn_tekuca=0;
for j=1:n-1
 for i=j+1:n
     ndn_tekuca=ndn_tekuca+(A(i,j)*A(i,j));
 end
end
     ndn_tekuca=sqrt(2*ndn_tekuca);

    %Proveravamo da li je odnos vandijagonalnih normi tekuce i polazne
    %matrice manji od epsilom
    if (ndn_tekuca<=eps*ndn)
        J=A;
        SV=Ubr;
        
       %ovo su sopstvene vrednosti
        svrednosti=diag(J);
      'ovo su sopstveni vektori'
        for i=1:n
         SV(:,i)
        end   
     
'sopstvene vrednosti:'
        return
    end
end
%polaznu matricu svodimo na 'skoro' dijagonalnu(zavisi od tacnosti))
