function [y, zf] = IIRfilt(x, B, A, zin)
%[y,zf] = IIRFILT(x, B, A, zin)
%IIRFILT vykoná filtráciu dát pomocou filtru daného čitateľom a menovateľom
%prenosu s daným počiatočným stavom filtru
% Vstupy:   x - vstupný signál filtru
%           B - vektor koeficientov čitateľa prenosu
%           A - vektor koeficientov menovateľa prenosu
%           zin - počiatočné podmienky pre diferenčnú rovnicu
% Výstup:   y - výstupný signál filtru
%           zf - konečný stav filtru, je možné použiť ako počiatočné
%           podmienky do ďalšej fázy, keby sme napríklad dlhý signál
%           rozdelili na menšie a filtrovali postupne
%[1] https://www.dsprelated.com/freebooks/filters/State_Space_Realization.html
%[2] https://www.dsprelated.com/freebooks/filters/State_Space_Filters.html

if nargin<3
   A = 1; 
end

assert(isnumeric(x)==1,'Vstupný signál musí pozostávať z číselných hodnôt');
assert(isnumeric(B)==1,'Čitateľ prenosu musí pozostávať z číselných hodnôt');
assert(isnumeric(A)==1,'Menovateľ prenosu musí pozostávať z číselných hodnôt');

b = size(B,1);
a = size(A,1);

assert(a==b,'Počet sekcií čitateľa a menovateľa musí byť rovnaký');

A = IIRtruncate(A); %nuly vpredu naviac robia zle
B = IIRtruncate(B);

if A(1)~=1
    A = A/A(1);
end



a = length(A);
b = length(B);

n = max(a,b);
A(n+1)=0; %potrebujeme ich mať rovnakej dĺžky kvôli for-cyklu
B(n+1)=0;
zin(n) = 0; %ak nie je zadaný na vstupe, vytvoria sa samé nuly  
assert(length(zin)<=n,'Vektor počiatočného stavu je pridlhý');
y = zeros(1,length(x));

%% FILTRACIA (STATE-SPACE)[1],[2]

for m = 1:length(y)
   y(m) = B(1) * x(m) + zin(1);
   
   for i = 2:n
      zin(i - 1) = B(i) * x(m) + zin(i) - A(i) * y(m);
   end
end
zf = zin(1:n - 1);

end

