BRDFLafortuneFitting.Program.lnsrch C# (CSharp) Method

lnsrch() protected static method

protected static lnsrch ( int n, double xold, double fold, double g, double p, double x, double &f, double stpmax, int &check, BFGSFunctionEval _FunctionEval, object _Params ) : void
n int
xold double
fold double
g double
p double
x double
f double
stpmax double
check int
_FunctionEval BFGSFunctionEval
_Params object
return void
        protected static void lnsrch( int n, double[] xold, double fold, double[] g, double[] p, double[] x, out double f, double stpmax, out int check, BFGSFunctionEval _FunctionEval, object _Params )
        {
            int i;
            double a,alam,alam2 = 0.0,alamin,b,disc,f2 = 0.0,fold2 = 0.0,rhs1,rhs2,slope,sum,temp,test,tmplam;

            check=0;
            for ( sum=0.0,i=1; i <= n; i++ )
                sum += p[i]*p[i];
            sum = Math.Sqrt( sum );

            if ( sum > stpmax )
                for ( i=1; i <= n; i++ )
                    p[i] *= stpmax / sum;

            for ( slope=0.0,i=1; i <= n; i++ )
                slope += g[i] * p[i];

            test = 0.0;
            for ( i=1; i <= n; i++ )
            {
                temp = Math.Abs( p[i] ) / Math.Max( Math.Abs( xold[i] ), 1.0 );
                if ( temp > test )
                    test = temp;
            }

            alamin = TOLY / test;
            alam = 1.0;
            int	IterationsCount = 0;
            while ( true )
            {
                IterationsCount++;

                for ( i=1; i <= n; i++ )
                    x[i] = xold[i] + alam * p[i];

                f = _FunctionEval( x, _Params );
                if ( double.IsInfinity( f ) )
                    throw new Exception( "Infinity!" );
                ENSUREVALID( x );
                if ( alam < alamin )
                {
                    for ( i=1; i <= n; i++ )
                        x[i] = xold[i];

                    check = 1;
                    return;
                }
                else if ( f <= fold + ALF * alam * slope )
                    return;
                else
                {
                    if ( alam == 1.0 )
                        tmplam = -slope / (2.0 * (f - fold-slope));
                    else
                    {
                        rhs1 = f-fold-alam*slope;
                        rhs2 = f2-fold2-alam2*slope;
                        a=(rhs1/(alam*alam)-rhs2/(alam2*alam2))/(alam-alam2);
                        b=(-alam2*rhs1/(alam*alam)+alam*rhs2/(alam2*alam2))/(alam-alam2);
                        if (a == 0.0) tmplam = -slope/(2.0*b);
                        else
                        {
                            disc = b*b - 3.0 * a * slope;
                            if ( disc < 0.0 )
                                throw new Exception( "Roundoff problem in lnsrch." );
                            else
                                tmplam = (-b + Math.Sqrt( disc ) ) / (3.0 * a);
                        }
                        if ( tmplam > 0.5 * alam )
                            tmplam = 0.5 * alam;
                    }
                }
                alam2=alam;
                f2 = f;
                fold2=fold;
                alam = Math.Max( tmplam, 0.1*alam );
            }
        }