%% Polinominterpoláció hibabecslése - Interpoláció Csebisev-alappontokon - Hermite-Fejér-interpoláció - Spline-interpoláció
%  1. Az f(x)=ln(x+1) függvényt interpoláljuk a 0, 0.6, 0.9 pontokban. Adjunk felső becslést a 0.45 pontban az interpolációs hibára!

f=@(x)log(x+1);
x0=0.45;
x=[0,0.6,0.9];
xx=linspace(0,0.9,100);
z=polyfit(x,f(x),2);
yy=polyval(z,xx);
plot(x,f(x),'or',xx,yy,'b-',xx,f(xx),'-k')
legend('adott pontok','interpolációs polinom','f(x)')
hiba_x0ban=(f(x0)-polyval(z,x0))

%
% 2. A [0,\pi] intervallumon akarjuk a \sin(x) függvényt interpolálni ekvidisztáns osztópontokon szakaszonként lineáris függvénnyel. Milyen messze legyenek a pontok legfeljebb, hogy az intervallum egyik pontjában se legyen nagyobb az eltérés az interpolációs függvény és az eredeti függvény között, mint 0.001?

f=@(x)sin(x);
x0=0.3;
n=4 % osztóintervallumok száma
x=linspace(0,pi,n+1);
xx=linspace(0,pi,100);
yy=interp1(x,f(x),xx,'linear');
plot(x,f(x),'or',xx,yy,'b-',xx,f(xx),'-k')
legend('adott pontok','interpolációs polinom','f(x)')
hiba_x0ban=f(x0)-interp1(x,f(x),x0,'linear')

%
% 3. Interpoláljuk az f(x)=1/(1+x^2) függvényt a [-5,5]intervallumon ekvidisztáns és Csebisev-alappontokban! Figyeljük meg, hogy hogyan változik az interpolációs hiba az osztópontok számának növelésével! (A program az ekvidisztáns esetet valósítja meg. Írjuk át Csebisev-interpolációra!)

f=@(x)1./(1+x.^2);
for n=3:12 % n+1 az osztópontok száma
x=linspace(-5,5,n+1);
y=f(x);
z=polyfit(x,y,n);
xx=linspace(-5,5,200);
yy=polyval(z,xx);
pause(0.5)
plot(x,y,'ro',xx,yy,'b-',xx,f(xx),'k-')
end

%
% 4. Az  x^3,\ x\in [-1,1]
%  függvényt interpoláljuk 3 Csebisev-alappont segítségével. Írjuk fel az interpolációs polinomot és mutassuk meg, hogy az interpolációs hiba egyik pontban sem lesz 1/4-nél nagyobb!

f=@(x)x.^3;
x=cos([pi/6,pi/6+pi/3, pi/6+2*pi/3]);
y=f(x);
z=polyfit(x,y,2);
xx=linspace(-1,1,100);
yy=polyval(z,xx);
plot(x,y,'ro',xx,yy,'b-',xx,f(xx),'k-')

%
% 5. Adjuk meg azt a legalacsonyabbfokú p(x) polinomot, amelyrep(1)=2, p(3)=1, p^\prime(1)=1, p^\prime(3)=2 !
%
% 6. Adjuk meg az (1,2), (2,1), (3,1) pontokra illeszkedő szakaszonként harmadfokú természetes spline-függvényt !

x=[1,2,3], y=[2,1,1]
d=[2,1,0;1,4,1;0,1,2]\[-1;-1;0]*3/1

xx=linspace(1,3,100);
sp=spline(x,[d(1),y,d(end)]);
sp.coefs

yy=ppval(sp,xx);
plot(xx,yy,'b-',x,y,'ro')

%
%% Trigonometrikus interpoláció
%  1. Interpoláljuk trigonometrikus polinommal az f(x)=|x-\pi| függvényt egyre több alappont esetén! 4 alappont esetén határozzuk meg papíron számolva is az együtthatókat!

n=3; % n+1 az alappontok száma

k=0:n;
x=k*2*pi/(n+1);
y=abs(x-pi);

xx=linspace(0,2*pi,200);

if mod(n,2)==1 
    m=(n+1)/2

X=kron([0:m]',x);
XX=kron([0:m]',xx);    
    
a=2*cos(X)*y'/(n+1);
a(1)=a(1)/2;
a(end)=a(end)/2
b=2*sin(X(2:m,:))*y'/(n+1)

yy=ones(1,m+1)*(diag(a)*cos(XX))+ones(1,m-1)*(diag(b)*sin(XX(2:end-1,:)));
plot(x,y,'ro',xx,yy,'b-')

else 
    m=n/2 

X=kron([0:m]',x);
XX=kron([0:m]',xx);    
    
a=2*cos(X)*y'/(n+1);
a(1)=a(1)/2
b=2*sin(X(2:m+1,:))*y'/(n+1)

yy=ones(1,m+1)*(diag(a)*cos(XX))+ones(1,m)*(diag(b)*sin(XX(2:end,:)));
plot(x,y,'ro',xx,yy,'b-')

end

%
% 2. A következő kód egy 2\pi periodikus zajos jelből ad meg 256 ekvidisztáns pontban egy mintavételi vektort. Diszkrét Fourier-transzformációt használva, az előző feladat kódjának átírásával simítsuk ki a jelet!

x=linspace(0,2*pi,257);
x=x(1:256);
y=sin(3*x).*cos(4*x)-sin(x).^2;
y=y+rand(1,256)*0.1;
y=y+rand(1,256)*0.3;
plot(x,y)
xlabel('idő')
ylabel('jelerősség')