function A=PowCoeffs(X,Y)

% визначаємо кількість елементів вектора X та транспонуємо у випадку, якщо
% подано вектор-рядок
[m,n]=size(X);
if m==1
    X=X';
    [m,n]=size(X);
end

% якщо передано лише один аргумент - це значення функції, а значення
% аргументу будуємо
if nargin==1
    Y=X;
    X=[1:m];
    X=X';
else
    % якщо Y не транспоновано - транспонуємо
    [m1,n1]=size(Y);
    if m1==1
        Y=Y';
    end
end

Xt=X; Yt=Y;
A=zeros(1,7);
A(1)=min(Yt);  Yt=Yt-A(1);
A(2)=max(Yt);  Yt=Yt/A(2);
A(3)=min(Xt);  Xt=Xt-A(3);
A(4)=max(Xt);  Xt=Xt/A(4);

i=1;
index=1;
while i<=m
    if (Xt(i,1)~=0)
        Xt(index,1)=Xt(i,1);
        Yt(index,1)=Yt(i,1);
        index=index+1;
    end
    i=i+1;
end;
Xt=Xt(1:index-1,:); Yt=Yt(1:index-1,:);

C(1)=1; C(2)=1; C(3)=0; flag=0;
yOld=getFunction(Xt,Yt,C);

while (flag==0)
    C(2)=findC2(Xt,Yt,m,C);
    yNew=getFunction(Xt,Yt,C);
    C(3)=findC3(Xt,Yt,m,C);
    yNew=getFunction(Xt,Yt,C);
    C(1)=findC1(Xt,Yt,m,C);
    yNew=getFunction(Xt,Yt,C);
    if abs(yNew-yOld)<0.0001
        flag=1;
    end
    yOld=yNew;
end
A(1,5:7)=C;

% =========================================================================
function RES=findC1(X,Y,m,C)

mIter=1000;
cIter=0;
flag=0;
xOld=C(1);

while flag==0
    xb=X.^C(2); axb=xOld*xb;

    dydc=axb+C(3); dydc=dydc-Y; dydc=dydc*2; dydc=dydc.*xb; dydc=sum(dydc);
    dydc2=xb.*xb; dydc2=dydc2*2; dydc2=sum(dydc2);

    xNew=xOld-dydc/dydc2;
    cErr=abs(xNew-xOld);
    if (cErr<0.0001) || (cIter>mIter)
        flag=1;
    end
    cIter=cIter+1
    xOld=xNew;
end
RES=xNew;

% =========================================================================
function RES=findC2(X,Y,m,C)

mIter=1000;
cIter=0;
flag=0;
xOld=C(2);

while flag==0
    xb=X.^xOld; axb=C(1)*xb; axb2=2*axb;
    lnx=log(X);
    ln2x=lnx.*lnx;

    dydc=axb+C(3); dydc=axb-Y; dydc=dydc.*axb2; dydc=dydc.*lnx; dydc=sum(dydc);
    dydc2=axb2+C(3); dydc2=dydc2-Y; dydc2=dydc2.*axb2; dydc2=dydc2.*ln2x; dydc2=sum(dydc2);

    xNew=xOld-dydc/dydc2;
    cErr=abs(xNew-xOld);
    if (cErr<0.0001) || (cIter>mIter)
        flag=1;
    end
    cIter=cIter+1
    xOld=xNew;
end
RES=xNew;

% =========================================================================
function RES=findC3(X,Y,m,C)

mIter=1000;
cIter=0;
flag=0;
xOld=C(3);

while flag==0
    xb=X.^C(2); axb=C(1)*xb;

    dydc=axb+xOld; dydc=dydc-Y; dydc=dydc*2; dydc=sum(dydc);
    dydc2=2*m;

    xNew=xOld-dydc/dydc2;
    cErr=abs(xNew-xOld);
    if (cErr<0.0001) || (cIter>mIter)
        flag=1;
    end
    cIter=cIter+1
    xOld=xNew;
end
RES=xNew;

% =========================================================================
function RES=getFunction(X,Y,C)

RES=X.^C(2);
RES=RES*C(1);
RES=RES+C(3);
RES=RES-Y;
RES=RES.*RES;
RES=sum(RES);
