コード例 #1
0
ファイル: levenbergmarquardt.cs プロジェクト: akasolace/qlnet
        public override EndCriteria.Type minimize(Problem P, EndCriteria endCriteria) {
            EndCriteria.Type ecType = EndCriteria.Type.None;
            P.reset();
            Vector x_ = P.currentValue();
            currentProblem_ = P;
            initCostValues_ = P.costFunction().values(x_);
            int m = initCostValues_.size();
            int n = x_.size();

            Vector xx = new Vector(x_);
            Vector fvec = new Vector(m), diag = new Vector(n);

            int mode = 1;
            double factor = 1;
            int nprint = 0;
            int info = 0;
            int nfev =0;

            Matrix fjac = new Matrix(m, n);

            int ldfjac = m;
            
            List<int> ipvt = new InitializedList<int>(n);
            Vector qtf = new Vector(n), wa1 = new Vector(n), wa2 = new Vector(n), wa3 = new Vector(n), wa4 = new Vector(m);

            // call lmdif to minimize the sum of the squares of m functions
            // in n variables by the Levenberg-Marquardt algorithm.
            MINPACK.lmdif(m, n, xx, ref fvec,
                                     endCriteria.functionEpsilon(),
                                     xtol_,
                                     gtol_,
                                     endCriteria.maxIterations(),
                                     epsfcn_,
                                     diag, mode, factor,
                                     nprint, ref info, ref nfev, ref fjac,
                                     ldfjac, ref ipvt, ref qtf,
                                     wa1, wa2, wa3, wa4,
                                     fcn);
            info_ = info;
            // check requirements & endCriteria evaluation
            if(info == 0) throw new ApplicationException("MINPACK: improper input parameters");
            //if(info == 6) throw new ApplicationException("MINPACK: ftol is too small. no further " +
            //                                             "reduction in the sum of squares is possible.");

            if (info != 6) ecType = EndCriteria.Type.StationaryFunctionValue;
            //QL_REQUIRE(info != 5, "MINPACK: number of calls to fcn has reached or exceeded maxfev.");
            endCriteria.checkMaxIterations(nfev, ref ecType);
            if(info == 7) throw new ApplicationException("MINPACK: xtol is too small. no further " +
                                           "improvement in the approximate " +
                                           "solution x is possible.");
            if(info == 8) throw new ApplicationException("MINPACK: gtol is too small. fvec is " +
                                           "orthogonal to the columns of the " +
                                           "jacobian to machine precision.");
            // set problem
            x_ = new Vector(xx.GetRange(0, n));
            P.setCurrentValue(x_);
            P.setFunctionValue(P.costFunction().value(x_));

            return ecType;
        }
コード例 #2
0
ファイル: SteepestDescent.cs プロジェクト: akasolace/qlnet
        //! minimize the optimization problem P
        public override EndCriteria.Type minimize(Problem P, EndCriteria endCriteria)
        {
            EndCriteria.Type ecType = EndCriteria.Type.None;
            P.reset();
            Vector x_ = P.currentValue();
            int iterationNumber_ = 0;
            int stationaryStateIterationNumber_ = 0;
            lineSearch_.searchDirection = new Vector(x_.Count);
            bool end;

            // function and squared norm of gradient values;
            double normdiff;
            // classical initial value for line-search step
            double t = 1.0;
            // Set gold at the size of the optimization problem search direction
            Vector gold = new Vector(lineSearch_.searchDirection.Count);
            Vector gdiff = new Vector(lineSearch_.searchDirection.Count);

            P.setFunctionValue(P.valueAndGradient(gold, x_));
            lineSearch_.searchDirection = gold*-1.0;
            P.setGradientNormValue(Vector.DotProduct(gold, gold));
            normdiff = Math.Sqrt(P.gradientNormValue());

            do
            {
                // Linesearch
                t = lineSearch_.value(P, ref ecType, endCriteria, t);

                if (!(lineSearch_.succeed()))
                    throw new ApplicationException("line-search failed!");

                // End criteria
                // FIXME: it's never been used! ???
                // , normdiff
                end = endCriteria.value(iterationNumber_, ref stationaryStateIterationNumber_, true, P.functionValue(), Math.Sqrt(P.gradientNormValue()), lineSearch_.lastFunctionValue(), Math.Sqrt(lineSearch_.lastGradientNorm2()), ref ecType);

                // Updates
                // New point
                x_ = lineSearch_.lastX();
                // New function value
                P.setFunctionValue(lineSearch_.lastFunctionValue());
                // New gradient and search direction vectors
                gdiff = gold - lineSearch_.lastGradient();
                normdiff = Math.Sqrt(Vector.DotProduct(gdiff, gdiff));
                gold = lineSearch_.lastGradient();
                lineSearch_.searchDirection = gold*-1.0;
                // New gradient squared norm
                P.setGradientNormValue(lineSearch_.lastGradientNorm2());

                // Increase interation number
                ++iterationNumber_;
            } while (end == false);

            P.setCurrentValue(x_);
            return ecType;

        }
コード例 #3
0
ファイル: ArmijoLineSearch.cs プロジェクト: Yenyenx/qlnet
        //! Perform line search
        public override double value(Problem P, ref EndCriteria.Type ecType, EndCriteria endCriteria, double t_ini)
        {
            //OptimizationMethod& method = P.method();
            Constraint constraint = P.constraint();
            succeed_ = true;
            bool maxIter = false;
            double qtold;
            double t = t_ini;
            int loopNumber = 0;

            double q0 = P.functionValue();
            double qp0 = P.gradientNormValue();

            qt_ = q0;
            qpt_ = (gradient_.Count == 0) ? qp0 : -Vector.DotProduct(gradient_, searchDirection_);

            // Initialize gradient
            gradient_ = new Vector(P.currentValue().Count);
            // Compute new point
            xtd_ = (Vector)P.currentValue().Clone();
            t = update(ref xtd_, searchDirection_, t, constraint);
            // Compute function value at the new point
            qt_ = P.value(xtd_);

            // Enter in the loop if the criterion is not satisfied
            if ((qt_ - q0) > -alpha_ * t * qpt_) {
                do {
                    loopNumber++;
                    // Decrease step
                    t *= beta_;
                    // Store old value of the function
                    qtold = qt_;
                    // New point value
                    xtd_ = P.currentValue();
                    t = update(ref xtd_, searchDirection_, t, constraint);

                    // Compute function value at the new point
                    qt_ = P.value(xtd_);
                    P.gradient(gradient_, xtd_);
                    // and it squared norm
                    maxIter = endCriteria.checkMaxIterations(loopNumber, ref ecType);
                } while ((((qt_ - q0) > (-alpha_ * t * qpt_)) || ((qtold - q0) <= (-alpha_ * t * qpt_ / beta_))) && (!maxIter));
            }

            if (maxIter)
                succeed_ = false;

            // Compute new gradient
            P.gradient(gradient_, xtd_);
            // and it squared norm
            qpt_ = Vector.DotProduct(gradient_, gradient_);

            // Return new step value
            return t;
        }
コード例 #4
0
ファイル: T_Optimizers.cs プロジェクト: akasolace/qlnet
 public void nestedOptimizationTest()
 {
     //("Testing nested optimizations...");
     OptimizationBasedCostFunction optimizationBasedCostFunction = new OptimizationBasedCostFunction();
     NoConstraint constraint = new NoConstraint();
     Vector initialValues = new Vector(1, 0.0);
     Problem problem = new Problem(optimizationBasedCostFunction, constraint, initialValues);
     LevenbergMarquardt optimizationMethod = new LevenbergMarquardt();
     //Simplex optimizationMethod(0.1);
     //ConjugateGradient optimizationMethod;
     //SteepestDescent optimizationMethod;
     EndCriteria endCriteria = new EndCriteria(1000, 100, 1e-5, 1e-5, 1e-5);
     optimizationMethod.minimize(problem, endCriteria);
 }
コード例 #5
0
ファイル: pseudosqrt.cs プロジェクト: Yenyenx/qlnet
        // Optimization function for hypersphere and lower-diagonal algorithm
        private static Matrix hypersphereOptimize(Matrix targetMatrix, Matrix currentRoot, bool lowerDiagonal)
        {
            int i,j,k,size = targetMatrix.rows();
            Matrix result = new Matrix(currentRoot);
            Vector variance = new Vector(size);
            for (i=0; i<size; i++){
                variance[i]=Math.Sqrt(targetMatrix[i,i]);
            }
            if (lowerDiagonal) {
                Matrix approxMatrix = result*Matrix.transpose(result);
                result = MatrixUtilities.CholeskyDecomposition(approxMatrix, true);
                for (i=0; i<size; i++) {
                    for (j=0; j<size; j++) {
                        result[i,j]/=Math.Sqrt(approxMatrix[i,i]);
                    }
                }
            } else {
                for (i=0; i<size; i++) {
                    for (j=0; j<size; j++) {
                        result[i,j]/=variance[i];
                    }
                }
            }

            ConjugateGradient optimize = new ConjugateGradient();
            EndCriteria endCriteria = new EndCriteria(100, 10, 1e-8, 1e-8, 1e-8);
            HypersphereCostFunction costFunction = new HypersphereCostFunction(targetMatrix, variance, lowerDiagonal);
            NoConstraint constraint = new NoConstraint();

            // hypersphere vector optimization

            if (lowerDiagonal) {
                Vector theta = new Vector(size * (size-1)/2);
                const double eps=1e-16;
                for (i=1; i<size; i++) {
                    for (j=0; j<i; j++) {
                        theta[i*(i-1)/2+j]=result[i,j];
                        if (theta[i*(i-1)/2+j]>1-eps)
                            theta[i*(i-1)/2+j]=1-eps;
                        if (theta[i*(i-1)/2+j]<-1+eps)
                            theta[i*(i-1)/2+j]=-1+eps;
                        for (k=0; k<j; k++) {
                            theta[i*(i-1)/2+j] /= Math.Sin(theta[i*(i-1)/2+k]);
                            if (theta[i*(i-1)/2+j]>1-eps)
                                theta[i*(i-1)/2+j]=1-eps;
                            if (theta[i*(i-1)/2+j]<-1+eps)
                                theta[i*(i-1)/2+j]=-1+eps;
                        }
                        theta[i*(i-1)/2+j] = Math.Acos(theta[i*(i-1)/2+j]);
                        if (j==i-1) {
                            if (result[i,i]<0)
                                theta[i*(i-1)/2+j]=-theta[i*(i-1)/2+j];
                        }
                    }
                }
                Problem p = new Problem(costFunction, constraint, theta);
                optimize.minimize(p, endCriteria);
                theta = p.currentValue();
                result.fill(1);
                for (i=0; i<size; i++) {
                    for (k=0; k<size; k++) {
                        if (k>i) {
                            result[i,k]=0;
                        } else {
                            for (j=0; j<=k; j++) {
                                if (j == k && k!=i)
                                    result[i,k] *= Math.Cos(theta[i*(i-1)/2+j]);
                                else if (j!=i)
                                    result[i,k] *= Math.Sin(theta[i*(i-1)/2+j]);
                            }
                        }
                    }
                }
            } else {
                Vector theta = new Vector(size * (size-1));
                const double eps=1e-16;
                for (i=0; i<size; i++) {
                    for (j=0; j<size-1; j++) {
                        theta[j*size+i]=result[i,j];
                        if (theta[j*size+i]>1-eps)
                            theta[j*size+i]=1-eps;
                        if (theta[j*size+i]<-1+eps)
                            theta[j*size+i]=-1+eps;
                        for (k=0;k<j;k++) {
                            theta[j*size+i] /= Math.Sin(theta[k*size+i]);
                            if (theta[j*size+i]>1-eps)
                                theta[j*size+i]=1-eps;
                            if (theta[j*size+i]<-1+eps)
                                theta[j*size+i]=-1+eps;
                        }
                        theta[j*size+i] = Math.Acos(theta[j*size+i]);
                        if (j==size-2) {
                            if (result[i,j+1]<0)
                                theta[j*size+i]=-theta[j*size+i];
                        }
                    }
                }
                Problem p = new Problem(costFunction, constraint, theta);
                optimize.minimize(p, endCriteria);
                theta=p.currentValue();
                result.fill(1);
                for (i = 0; i < size; i++) {
                    for (k=0; k<size; k++) {
                        for (j=0; j<=k; j++) {
                            if (j == k && k!=size-1)
                                result[i,k] *= Math.Cos(theta[j*size+i]);
                            else if (j!=size-1)
                                result[i,k] *= Math.Sin(theta[j*size+i]);
                        }
                    }
                }
            }

            for (i=0; i<size; i++) {
                for (j=0; j<size; j++) {
                    result[i,j]*=variance[i];
                }
            }
            return result;
        }
コード例 #6
0
        public void compute()
        {
            if (vegaWeighted_)
            {
                double weightsSum = 0.0;
                for (int i = 0; i < times_.Count; i++)
                {
                    double stdDev = Math.Sqrt(blackVols_[i] * blackVols_[i] * times_[i]);
                    // when strike==forward, the blackFormulaStdDevDerivative becomes
                    weights_[i] = new CumulativeNormalDistribution().derivative(.5 * stdDev);
                    weightsSum += weights_[i];
                }
                // weight normalization
                for (int i = 0; i < times_.Count; i++)
                {
                    weights_[i] /= weightsSum;
                }
            }
            // there is nothing to optimize
            if (aIsFixed_ && bIsFixed_ && cIsFixed_ && dIsFixed_)
            {
                abcdEndCriteria_ = QLNet.EndCriteria.Type.None;
                return;
            }
            else
            {
                AbcdError costFunction = new AbcdError(this);
                transformation_ = new AbcdParametersTransformation();

                Vector guess = new Vector(4);
                guess[0] = a_;
                guess[1] = b_;
                guess[2] = c_;
                guess[3] = d_;

                List <bool> parameterAreFixed = new InitializedList <bool>(4);
                parameterAreFixed[0] = aIsFixed_;
                parameterAreFixed[1] = bIsFixed_;
                parameterAreFixed[2] = cIsFixed_;
                parameterAreFixed[3] = dIsFixed_;

                Vector inversedTransformatedGuess = new Vector(transformation_.inverse(guess));

                ProjectedCostFunction projectedAbcdCostFunction = new ProjectedCostFunction(costFunction,
                                                                                            inversedTransformatedGuess, parameterAreFixed);

                Vector projectedGuess = new Vector(projectedAbcdCostFunction.project(inversedTransformatedGuess));

                NoConstraint constraint = new NoConstraint();
                Problem      problem    = new Problem(projectedAbcdCostFunction, constraint, projectedGuess);
                abcdEndCriteria_ = optMethod_.minimize(problem, endCriteria_);
                Vector projectedResult = new Vector(problem.currentValue());
                Vector transfResult    = new Vector(projectedAbcdCostFunction.include(projectedResult));

                Vector result = transformation_.direct(transfResult);
                QLNet.AbcdMathFunction.validate(a_, b_, c_, d_);
                a_ = result[0];
                b_ = result[1];
                c_ = result[2];
                d_ = result[3];
            }
        }
コード例 #7
0
ファイル: Simplex.cs プロジェクト: vdt/QLNet
        public override EndCriteria.Type minimize(Problem P, EndCriteria endCriteria)
        {
            // set up of the problem
            //double ftol = endCriteria.functionEpsilon();    // end criteria on f(x) (see Numerical Recipes in C++, p.410)
            double xtol = endCriteria.rootEpsilon(); // end criteria on x (see GSL v. 1.9, http://www.gnu.org/software/gsl/)
            int maxStationaryStateIterations_ = endCriteria.maxStationaryStateIterations();
            EndCriteria.Type ecType = EndCriteria.Type.None;
            P.reset();
            Vector x_ = P.currentValue();
            int iterationNumber_ = 0;

            // Initialize vertices of the simplex
            bool end = false;
            int n = x_.Count;
            vertices_ = new InitializedList<Vector>(n + 1, x_);
            for (int i = 0; i < n; i++)
            {
                Vector direction = new Vector(n, 0.0);
                direction[i] = 1.0;
                P.constraint().update(vertices_[i + 1], direction, lambda_);
            }
            // Initialize function values at the vertices of the simplex
            values_ = new Vector(n + 1, 0.0);
            for (int i = 0; i <= n; i++)
                values_[i] = P.value(vertices_[i]);
            // Loop looking for minimum
            do
            {
                sum_ = new Vector(n, 0.0);
                for (int i = 0; i <= n; i++)
                    sum_ += vertices_[i];
                // Determine the best (iLowest), worst (iHighest)
                // and 2nd worst (iNextHighest) vertices
                int iLowest = 0;
                int iHighest;
                int iNextHighest;
                if (values_[0] < values_[1])
                {
                    iHighest = 1;
                    iNextHighest = 0;
                }
                else
                {
                    iHighest = 0;
                    iNextHighest = 1;
                }
                for (int i = 1; i <= n; i++)
                {
                    if (values_[i] > values_[iHighest])
                    {
                        iNextHighest = iHighest;
                        iHighest = i;
                    }
                    else
                    {
                        if ((values_[i] > values_[iNextHighest]) && i != iHighest)
                            iNextHighest = i;
                    }
                    if (values_[i] < values_[iLowest])
                        iLowest = i;
                }
                // Now compute accuracy, update iteration number and check end criteria
                //// Numerical Recipes exit strategy on fx (see NR in C++, p.410)
                //double low = values_[iLowest];
                //double high = values_[iHighest];
                //double rtol = 2.0*std::fabs(high - low)/
                //    (std::fabs(high) + std::fabs(low) + QL_EPSILON);
                //++iterationNumber_;
                //if (rtol < ftol ||
                //    endCriteria.checkMaxIterations(iterationNumber_, ecType)) {
                // GSL exit strategy on x (see GSL v. 1.9, http://www.gnu.org/software/gsl
                double simplexSize = Utils.computeSimplexSize(vertices_);
                ++iterationNumber_;
                if (simplexSize < xtol || endCriteria.checkMaxIterations(iterationNumber_, ref ecType))
                {
                    endCriteria.checkStationaryPoint(0.0, 0.0, ref maxStationaryStateIterations_, ref ecType);
                    endCriteria.checkMaxIterations(iterationNumber_, ref ecType);
                    x_ = vertices_[iLowest];
                    double low = values_[iLowest];
                    P.setFunctionValue(low);
                    P.setCurrentValue(x_);
                    return ecType;
                }
                // If end criteria is not met, continue
                double factor = -1.0;
                double vTry = extrapolate(ref P, iHighest, ref factor);
                if ((vTry <= values_[iLowest]) && (factor == -1.0))
                {
                    factor = 2.0;
                    extrapolate(ref P, iHighest, ref factor);
                }
                else if (Math.Abs(factor) > Const.QL_Epsilon)
                {
                    if (vTry >= values_[iNextHighest])
                    {
                        double vSave = values_[iHighest];
                        factor = 0.5;
                        vTry = extrapolate(ref P, iHighest, ref factor);
                        if (vTry >= vSave && Math.Abs(factor) > Const.QL_Epsilon)
                        {
                            for (int i = 0; i <= n; i++)
                            {
                                if (i != iLowest)
                                {
            #if QL_ARRAY_EXPRESSIONS
                                    vertices_[i] = 0.5 * (vertices_[i] + vertices_[iLowest]);
            #else
                                    vertices_[i] += vertices_[iLowest];
                                    vertices_[i] *= 0.5;
            #endif
                                    values_[i] = P.value(vertices_[i]);
                                }
                            }
                        }
                    }
                }
                // If can't extrapolate given the constraints, exit
                if (Math.Abs(factor) <= Const.QL_Epsilon)
                {
                    x_ = vertices_[iLowest];
                    double low = values_[iLowest];
                    P.setFunctionValue(low);
                    P.setCurrentValue(x_);
                    return EndCriteria.Type.StationaryFunctionValue;
                }
            } while (end == false);
            throw new ApplicationException("optimization failed: unexpected behaviour");
        }
コード例 #8
0
ファイル: method.cs プロジェクト: ammachado/QLNet
 //! minimize the optimization problem P
 public abstract EndCriteria.Type minimize(Problem P, EndCriteria endCriteria);
コード例 #9
0
        public override EndCriteria.Type minimize(Problem P, EndCriteria endCriteria)
        {
            // Initializations
            double ftol = endCriteria.functionEpsilon();
            int    maxStationaryStateIterations_ = endCriteria.maxStationaryStateIterations();

            EndCriteria.Type ecType = EndCriteria.Type.None; // reset end criteria
            P.reset();                                       // reset problem
            Vector x_ = P.currentValue();                    // store the starting point
            int    iterationNumber_ = 0;

            // dimension line search
            lineSearch_.searchDirection = new Vector(x_.size());
            bool done = false;

            // function and squared norm of gradient values
            double fnew, fold, gold2;
            double fdiff;
            // classical initial value for line-search step
            double t = 1.0;
            // Set gradient g at the size of the optimization problem
            // search direction
            int    sz = lineSearch_.searchDirection.size();
            Vector prevGradient = new Vector(sz), d = new Vector(sz), sddiff = new Vector(sz), direction = new Vector(sz);

            // Initialize cost function, gradient prevGradient and search direction
            P.setFunctionValue(P.valueAndGradient(ref prevGradient, x_));
            P.setGradientNormValue(Vector.DotProduct(prevGradient, prevGradient));
            lineSearch_.searchDirection = prevGradient * -1;

            bool first_time = true;

            // Loop over iterations
            do
            {
                // Linesearch
                if (!first_time)
                {
                    prevGradient = lineSearch_.lastGradient();
                }
                t = (lineSearch_.value(P, ref ecType, endCriteria, t));
                // don't throw: it can fail just because maxIterations exceeded
                if (lineSearch_.succeed())
                {
                    // Updates

                    // New point
                    x_ = lineSearch_.lastX();
                    // New function value
                    fold = P.functionValue();
                    P.setFunctionValue(lineSearch_.lastFunctionValue());
                    // New gradient and search direction vectors

                    // orthogonalization coef
                    gold2 = P.gradientNormValue();
                    P.setGradientNormValue(lineSearch_.lastGradientNorm2());

                    // conjugate gradient search direction
                    direction = getUpdatedDirection(P, gold2, prevGradient);

                    sddiff = direction - lineSearch_.searchDirection;
                    lineSearch_.searchDirection = direction;
                    // Now compute accuracy and check end criteria
                    // Numerical Recipes exit strategy on fx (see NR in C++, p.423)
                    fnew  = P.functionValue();
                    fdiff = 2.0 * Math.Abs(fnew - fold) /
                            (Math.Abs(fnew) + Math.Abs(fold) + Const.QL_EPSILON);
                    P.setCurrentValue(x_);   // update problem current value
                    if (fdiff < ftol ||
                        endCriteria.checkMaxIterations(iterationNumber_, ref ecType))
                    {
                        endCriteria.checkStationaryFunctionValue(0.0, 0.0, ref maxStationaryStateIterations_, ref ecType);
                        endCriteria.checkMaxIterations(iterationNumber_, ref ecType);
                        return(ecType);
                    }
                    ++iterationNumber_;    // Increase iteration number
                    first_time = false;
                }
                else
                {
                    done = true;
                }
            }while (!done);
            P.setCurrentValue(x_);
            return(ecType);
        }
コード例 #10
0
 //! computes the new search direction
 protected virtual Vector getUpdatedDirection(Problem P, double gold2, Vector gradient)
 {
     throw new NotImplementedException();
 }
コード例 #11
0
ファイル: LineSearch.cs プロジェクト: sandboxorg/QLNet
 //! Perform line search
 public abstract double value(Problem P, ref EndCriteria.Type ecType, EndCriteria NamelessParameter3, double t_ini); // initial value of line-search step
コード例 #12
0
        //! solve the optimization problem P
        public override EndCriteria.Type minimize(Problem P, EndCriteria endCriteria)
        {
            // Initializations
            double ftol = endCriteria.functionEpsilon();
            int    maxStationaryStateIterations_ = endCriteria.maxStationaryStateIterations();

            EndCriteria.Type ecType = EndCriteria.Type.None;    // reset end criteria
            P.reset();                                          // reset problem
            Vector x_ = P.currentValue();                       // store the starting point
            int    iterationNumber_ = 0;                        // stationaryStateIterationNumber_=0

            lineSearch_.searchDirection = new Vector(x_.Count); // dimension line search
            bool done = false;

            // function and squared norm of gradient values;
            double fnew;
            double fold;
            double gold2;
            double c;
            double fdiff;
            double normdiff;
            // classical initial value for line-search step
            double t = 1.0;
            // Set gradient g at the size of the optimization problem search direction
            int    sz     = lineSearch_.searchDirection.Count;
            Vector g      = new Vector(sz);
            Vector d      = new Vector(sz);
            Vector sddiff = new Vector(sz);

            // Initialize cost function, gradient g and search direction
            P.setFunctionValue(P.valueAndGradient(g, x_));
            P.setGradientNormValue(Vector.DotProduct(g, g));
            lineSearch_.searchDirection = g * -1.0;
            // Loop over iterations
            do
            {
                // Linesearch
                t = lineSearch_.value(P, ref ecType, endCriteria, t);
                // don't throw: it can fail just because maxIterations exceeded
                //QL_REQUIRE(lineSearch_->succeed(), "line-search failed!");
                if (lineSearch_.succeed())
                {
                    // Updates
                    d = lineSearch_.searchDirection;
                    // New point
                    x_ = lineSearch_.lastX();
                    // New function value
                    fold = P.functionValue();
                    P.setFunctionValue(lineSearch_.lastFunctionValue());
                    // New gradient and search direction vectors
                    g = lineSearch_.lastGradient();
                    // orthogonalization coef
                    gold2 = P.gradientNormValue();
                    P.setGradientNormValue(lineSearch_.lastGradientNorm2());
                    c = P.gradientNormValue() / gold2;
                    // conjugate gradient search direction
                    sddiff   = ((g * -1.0) + c * d) - lineSearch_.searchDirection;
                    normdiff = Math.Sqrt(Vector.DotProduct(sddiff, sddiff));
                    lineSearch_.searchDirection = (g * -1.0) + c * d;
                    // Now compute accuracy and check end criteria
                    // Numerical Recipes exit strategy on fx (see NR in C++, p.423)
                    fnew  = P.functionValue();
                    fdiff = 2.0 * Math.Abs(fnew - fold) / (Math.Abs(fnew) + Math.Abs(fold) + Double.Epsilon);
                    if (fdiff < ftol || endCriteria.checkMaxIterations(iterationNumber_, ref ecType))
                    {
                        endCriteria.checkStationaryFunctionValue(0.0, 0.0, ref maxStationaryStateIterations_, ref ecType);
                        endCriteria.checkMaxIterations(iterationNumber_, ref ecType);
                        return(ecType);
                    }
                    //done = endCriteria(iterationNumber_,
                    //                   stationaryStateIterationNumber_,
                    //                   true,  //FIXME: it should be in the problem
                    //                   fold,
                    //                   std::sqrt(gold2),
                    //                   P.functionValue(),
                    //                   std::sqrt(P.gradientNormValue()),
                    //                   ecType);
                    P.setCurrentValue(x_);                  // update problem current value
                    ++iterationNumber_;                     // Increase iteration number
                }
                else
                {
                    done = true;
                }
            } while (!done);
            P.setCurrentValue(x_);
            return(ecType);
        }
コード例 #13
0
        public override EndCriteria.Type minimize(Problem P, EndCriteria endCriteria)
        {
            EndCriteria.Type ecType = EndCriteria.Type.None;
            P.reset();
            Vector x_ = P.currentValue();

            currentProblem_ = P;
            initCostValues_ = P.costFunction().values(x_);
            int m = initCostValues_.size();
            int n = x_.size();

            Vector xx = new Vector(x_);
            Vector fvec = new Vector(m), diag = new Vector(n);

            int    mode   = 1;
            double factor = 1;
            int    nprint = 0;
            int    info   = 0;
            int    nfev   = 0;

            Matrix fjac = new Matrix(m, n);

            int ldfjac = m;

            List <int> ipvt = new InitializedList <int>(n);
            Vector     qtf = new Vector(n), wa1 = new Vector(n), wa2 = new Vector(n), wa3 = new Vector(n), wa4 = new Vector(m);

            // call lmdif to minimize the sum of the squares of m functions
            // in n variables by the Levenberg-Marquardt algorithm.
            MINPACK.lmdif(m, n, xx, ref fvec,
                          endCriteria.functionEpsilon(),
                          xtol_,
                          gtol_,
                          endCriteria.maxIterations(),
                          epsfcn_,
                          diag, mode, factor,
                          nprint, ref info, ref nfev, ref fjac,
                          ldfjac, ref ipvt, ref qtf,
                          wa1, wa2, wa3, wa4,
                          fcn);
            info_ = info;
            // check requirements & endCriteria evaluation
            if (info == 0)
            {
                throw new ApplicationException("MINPACK: improper input parameters");
            }
            //if(info == 6) throw new ApplicationException("MINPACK: ftol is too small. no further " +
            //                                             "reduction in the sum of squares is possible.");

            if (info != 6)
            {
                ecType = EndCriteria.Type.StationaryFunctionValue;
            }
            //QL_REQUIRE(info != 5, "MINPACK: number of calls to fcn has reached or exceeded maxfev.");
            endCriteria.checkMaxIterations(nfev, ref ecType);
            if (info == 7)
            {
                throw new ApplicationException("MINPACK: xtol is too small. no further " +
                                               "improvement in the approximate " +
                                               "solution x is possible.");
            }
            if (info == 8)
            {
                throw new ApplicationException("MINPACK: gtol is too small. fvec is " +
                                               "orthogonal to the columns of the " +
                                               "jacobian to machine precision.");
            }
            // set problem
            x_ = new Vector(xx.GetRange(0, n));
            P.setCurrentValue(x_);
            P.setFunctionValue(P.costFunction().value(x_));

            return(ecType);
        }
コード例 #14
0
        // Optimization function for hypersphere and lower-diagonal algorithm
        private static Matrix hypersphereOptimize(Matrix targetMatrix, Matrix currentRoot, bool lowerDiagonal)
        {
            int    i, j, k, size = targetMatrix.rows();
            Matrix result   = new Matrix(currentRoot);
            Vector variance = new Vector(size);

            for (i = 0; i < size; i++)
            {
                variance[i] = Math.Sqrt(targetMatrix[i, i]);
            }
            if (lowerDiagonal)
            {
                Matrix approxMatrix = result * Matrix.transpose(result);
                result = MatrixUtilities.CholeskyDecomposition(approxMatrix, true);
                for (i = 0; i < size; i++)
                {
                    for (j = 0; j < size; j++)
                    {
                        result[i, j] /= Math.Sqrt(approxMatrix[i, i]);
                    }
                }
            }
            else
            {
                for (i = 0; i < size; i++)
                {
                    for (j = 0; j < size; j++)
                    {
                        result[i, j] /= variance[i];
                    }
                }
            }

            ConjugateGradient       optimize     = new ConjugateGradient();
            EndCriteria             endCriteria  = new EndCriteria(100, 10, 1e-8, 1e-8, 1e-8);
            HypersphereCostFunction costFunction = new HypersphereCostFunction(targetMatrix, variance, lowerDiagonal);
            NoConstraint            constraint   = new NoConstraint();

            // hypersphere vector optimization

            if (lowerDiagonal)
            {
                Vector       theta = new Vector(size * (size - 1) / 2);
                const double eps   = 1e-16;
                for (i = 1; i < size; i++)
                {
                    for (j = 0; j < i; j++)
                    {
                        theta[i * (i - 1) / 2 + j] = result[i, j];
                        if (theta[i * (i - 1) / 2 + j] > 1 - eps)
                        {
                            theta[i * (i - 1) / 2 + j] = 1 - eps;
                        }
                        if (theta[i * (i - 1) / 2 + j] < -1 + eps)
                        {
                            theta[i * (i - 1) / 2 + j] = -1 + eps;
                        }
                        for (k = 0; k < j; k++)
                        {
                            theta[i * (i - 1) / 2 + j] /= Math.Sin(theta[i * (i - 1) / 2 + k]);
                            if (theta[i * (i - 1) / 2 + j] > 1 - eps)
                            {
                                theta[i * (i - 1) / 2 + j] = 1 - eps;
                            }
                            if (theta[i * (i - 1) / 2 + j] < -1 + eps)
                            {
                                theta[i * (i - 1) / 2 + j] = -1 + eps;
                            }
                        }
                        theta[i * (i - 1) / 2 + j] = Math.Acos(theta[i * (i - 1) / 2 + j]);
                        if (j == i - 1)
                        {
                            if (result[i, i] < 0)
                            {
                                theta[i * (i - 1) / 2 + j] = -theta[i * (i - 1) / 2 + j];
                            }
                        }
                    }
                }
                Problem p = new Problem(costFunction, constraint, theta);
                optimize.minimize(p, endCriteria);
                theta = p.currentValue();
                result.fill(1);
                for (i = 0; i < size; i++)
                {
                    for (k = 0; k < size; k++)
                    {
                        if (k > i)
                        {
                            result[i, k] = 0;
                        }
                        else
                        {
                            for (j = 0; j <= k; j++)
                            {
                                if (j == k && k != i)
                                {
                                    result[i, k] *= Math.Cos(theta[i * (i - 1) / 2 + j]);
                                }
                                else if (j != i)
                                {
                                    result[i, k] *= Math.Sin(theta[i * (i - 1) / 2 + j]);
                                }
                            }
                        }
                    }
                }
            }
            else
            {
                Vector       theta = new Vector(size * (size - 1));
                const double eps   = 1e-16;
                for (i = 0; i < size; i++)
                {
                    for (j = 0; j < size - 1; j++)
                    {
                        theta[j * size + i] = result[i, j];
                        if (theta[j * size + i] > 1 - eps)
                        {
                            theta[j * size + i] = 1 - eps;
                        }
                        if (theta[j * size + i] < -1 + eps)
                        {
                            theta[j * size + i] = -1 + eps;
                        }
                        for (k = 0; k < j; k++)
                        {
                            theta[j * size + i] /= Math.Sin(theta[k * size + i]);
                            if (theta[j * size + i] > 1 - eps)
                            {
                                theta[j * size + i] = 1 - eps;
                            }
                            if (theta[j * size + i] < -1 + eps)
                            {
                                theta[j * size + i] = -1 + eps;
                            }
                        }
                        theta[j * size + i] = Math.Acos(theta[j * size + i]);
                        if (j == size - 2)
                        {
                            if (result[i, j + 1] < 0)
                            {
                                theta[j * size + i] = -theta[j * size + i];
                            }
                        }
                    }
                }
                Problem p = new Problem(costFunction, constraint, theta);
                optimize.minimize(p, endCriteria);
                theta = p.currentValue();
                result.fill(1);
                for (i = 0; i < size; i++)
                {
                    for (k = 0; k < size; k++)
                    {
                        for (j = 0; j <= k; j++)
                        {
                            if (j == k && k != size - 1)
                            {
                                result[i, k] *= Math.Cos(theta[j * size + i]);
                            }
                            else if (j != size - 1)
                            {
                                result[i, k] *= Math.Sin(theta[j * size + i]);
                            }
                        }
                    }
                }
            }

            for (i = 0; i < size; i++)
            {
                for (j = 0; j < size; j++)
                {
                    result[i, j] *= variance[i];
                }
            }
            return(result);
        }
コード例 #15
0
ファイル: ConjugateGradient.cs プロジェクト: ariesy/QLNet
        //! solve the optimization problem P
        public override EndCriteria.Type minimize(Problem P, EndCriteria endCriteria)
        {
            // Initializations
            double ftol = endCriteria.functionEpsilon();
            int maxStationaryStateIterations_ = endCriteria.maxStationaryStateIterations();
            EndCriteria.Type ecType = EndCriteria.Type.None; // reset end criteria
            P.reset(); // reset problem
            Vector x_ = P.currentValue(); // store the starting point
            int iterationNumber_ =0; // stationaryStateIterationNumber_=0
            lineSearch_.searchDirection = new Vector(x_.Count); // dimension line search
            bool done = false;

            // function and squared norm of gradient values;
            double fnew;
            double fold;
            double gold2;
            double c;
            double fdiff;
            double normdiff;
            // classical initial value for line-search step
            double t = 1.0;
            // Set gradient g at the size of the optimization problem search direction
            int sz = lineSearch_.searchDirection.Count;
            Vector g = new Vector(sz);
            Vector d = new Vector(sz);
            Vector sddiff = new Vector(sz);
            // Initialize cost function, gradient g and search direction
            P.setFunctionValue(P.valueAndGradient(g, x_));
            P.setGradientNormValue(Vector.DotProduct(g, g));
            lineSearch_.searchDirection = g * -1.0;
            // Loop over iterations
            do
            {
                // Linesearch
                t = lineSearch_.value(P, ref ecType, endCriteria, t);
                // don't throw: it can fail just because maxIterations exceeded
                //QL_REQUIRE(lineSearch_->succeed(), "line-search failed!");
                if (lineSearch_.succeed())
                {
                    // Updates
                    d = lineSearch_.searchDirection;
                    // New point
                    x_ = lineSearch_.lastX();
                    // New function value
                    fold = P.functionValue();
                    P.setFunctionValue(lineSearch_.lastFunctionValue());
                    // New gradient and search direction vectors
                    g = lineSearch_.lastGradient();
                    // orthogonalization coef
                    gold2 = P.gradientNormValue();
                    P.setGradientNormValue(lineSearch_.lastGradientNorm2());
                    c = P.gradientNormValue() / gold2;
                    // conjugate gradient search direction
                    sddiff = ((g*-1.0) + c * d) - lineSearch_.searchDirection;
                    normdiff = Math.Sqrt(Vector.DotProduct(sddiff, sddiff));
                    lineSearch_.searchDirection = (g*-1.0) + c * d;
                    // Now compute accuracy and check end criteria
                    // Numerical Recipes exit strategy on fx (see NR in C++, p.423)
                    fnew = P.functionValue();
                    fdiff = 2.0 *Math.Abs(fnew-fold) / (Math.Abs(fnew) + Math.Abs(fold) + Double.Epsilon);
                    if (fdiff < ftol || endCriteria.checkMaxIterations(iterationNumber_, ref ecType))
                    {
                        endCriteria.checkStationaryFunctionValue(0.0, 0.0, ref maxStationaryStateIterations_, ref ecType);
                        endCriteria.checkMaxIterations(iterationNumber_, ref ecType);
                        return ecType;
                    }
                    //done = endCriteria(iterationNumber_,
                    //                   stationaryStateIterationNumber_,
                    //                   true,  //FIXME: it should be in the problem
                    //                   fold,
                    //                   std::sqrt(gold2),
                    //                   P.functionValue(),
                    //                   std::sqrt(P.gradientNormValue()),
                    //                   ecType);
                    P.setCurrentValue(x_); // update problem current value
                    ++iterationNumber_; // Increase iteration number
                    }
                else
                {
                    done =true;
                }
            } while (!done);
            P.setCurrentValue(x_);
            return ecType;
        }
コード例 #16
0
ファイル: LineSearch.cs プロジェクト: akasolace/qlnet
 //! Perform line search
 public abstract double value(Problem P, ref EndCriteria.Type ecType, EndCriteria NamelessParameter3, double t_ini); // initial value of line-search step
コード例 #17
0
        public void calculate()
        {
            validCurve_ = false;
            int nInsts = ts_.instruments_.Count, i;

            // ensure rate helpers are sorted
            ts_.instruments_.Sort((x, y) => x.latestDate().CompareTo(y.latestDate()));

            // check that there is no instruments with the same maturity
            for (i = 1; i < nInsts; ++i)
            {
                Date m1 = ts_.instruments_[i - 1].latestDate(),
                     m2 = ts_.instruments_[i].latestDate();
                if (m1 == m2)
                {
                    throw new ArgumentException("two instruments have the same maturity (" + m1 + ")");
                }
            }

            // check that there is no instruments with invalid quote
            if ((i = ts_.instruments_.FindIndex(x => !x.quoteIsValid())) != -1)
            {
                throw new ArgumentException("instrument " + i + " (maturity: " + ts_.instruments_[i].latestDate() +
                                            ") has an invalid quote");
            }

            // setup instruments and register with them
            ts_.instruments_.ForEach(j => ts_.setTermStructure(j));

            // set initial guess only if the current curve cannot be used as guess
            if (validCurve_)
            {
                if (ts_.data_.Count != nInsts + 1)
                {
                    throw new ArgumentException("dimension mismatch: expected " + nInsts + 1 + ", actual " + ts_.data_.Count);
                }
            }
            else
            {
                ts_.data_    = new InitializedList <double>(nInsts + 1);
                ts_.data_[0] = ts_.initialValue();
            }

            // calculate dates and times
            ts_.dates_    = new InitializedList <Date>(nInsts + 1);
            ts_.times_    = new InitializedList <double>(nInsts + 1);
            ts_.dates_[0] = ts_.initialDate();
            ts_.times_[0] = ts_.timeFromReference(ts_.dates_[0]);
            for (i = 0; i < nInsts; ++i)
            {
                ts_.dates_[i + 1] = ts_.instruments_[i].latestDate();
                ts_.times_[i + 1] = ts_.timeFromReference(ts_.dates_[i + 1]);
                if (!validCurve_)
                {
                    ts_.data_[i + 1] = ts_.data_[i];
                }
            }

            LevenbergMarquardt solver           = new LevenbergMarquardt(ts_.accuracy_, ts_.accuracy_, ts_.accuracy_);
            EndCriteria        endCriteria      = new EndCriteria(100, 10, 0.00, ts_.accuracy_, 0.00);
            PositiveConstraint posConstraint    = new PositiveConstraint();
            NoConstraint       noConstraint     = new NoConstraint();
            Constraint         solverConstraint = forcePositive_ ? (Constraint)posConstraint : (Constraint)noConstraint;

            // now start the bootstrapping.
            int iInst = localisation_ - 1;

            int dataAdjust = (ts_.interpolator_ as ConvexMonotone).dataSizeAdjustment;

            do
            {
                int    initialDataPt = iInst + 1 - localisation_ + dataAdjust;
                Vector startArray    = new Vector(localisation_ + 1 - dataAdjust);
                for (int j = 0; j < startArray.size() - 1; ++j)
                {
                    startArray[j] = ts_.data_[initialDataPt + j];
                }

                // here we are extending the interpolation a point at a
                // time... but the local interpolator can make an
                // approximation for the final localisation period.
                // e.g. if the localisation is 2, then the first section
                // of the curve will be solved using the first 2
                // instruments... with the local interpolator making
                // suitable boundary conditions.
                ts_.interpolation_ = (ts_.interpolator_ as ConvexMonotone).localInterpolate(ts_.times_, iInst + 2, ts_.data_,
                                                                                            localisation_, ts_.interpolation_ as ConvexMonotoneInterpolation, nInsts + 1);

                if (iInst >= localisation_)
                {
                    startArray[localisation_ - dataAdjust] = ts_.guess(iInst, ts_, false, 0);
                }
                else
                {
                    startArray[localisation_ - dataAdjust] = ts_.data_[0];
                }

                var currentCost = new PenaltyFunction <T, U>(ts_, initialDataPt, ts_.instruments_,
                                                             iInst - localisation_ + 1, iInst + 1);
                Problem          toSolve = new Problem(currentCost, solverConstraint, startArray);
                EndCriteria.Type endType = solver.minimize(toSolve, endCriteria);

                // check the end criteria
                if (!(endType == EndCriteria.Type.StationaryFunctionAccuracy ||
                      endType == EndCriteria.Type.StationaryFunctionValue))
                {
                    throw new ApplicationException("Unable to strip yieldcurve to required accuracy ");
                }
                ++iInst;
            } while (iInst < nInsts);

            validCurve_ = true;
        }
コード例 #18
0
ファイル: Simplex.cs プロジェクト: vdt/QLNet
 private double extrapolate(ref Problem P, int iHighest, ref double factor)
 {
     Vector pTry;
     do
     {
         int dimensions = values_.Count - 1;
         double factor1 = (1.0 - factor) / dimensions;
         double factor2 = factor1 - factor;
         // #if QL_ARRAY_EXPRESSIONS
         pTry = sum_ * factor1 - vertices_[iHighest] * factor2;
         //#else
         //                    // composite expressions fail to compile with gcc 3.4 on windows
         //                    pTry = sum_ * factor1;
         //                    pTry -= vertices_[iHighest] * factor2;
         //#endif
         factor *= 0.5;
     } while (!P.constraint().test(pTry) && Math.Abs(factor) > Const.QL_Epsilon);
     if (Math.Abs(factor) <= Const.QL_Epsilon)
     {
         return values_[iHighest];
     }
     factor *= 2.0;
     double vTry = P.value(pTry);
     if (vTry < values_[iHighest])
     {
         values_[iHighest] = vTry;
         //#if QL_ARRAY_EXPRESSIONS
         sum_ += pTry - vertices_[iHighest];
         //#else
         //                    sum_ += pTry;
         //                    sum_ -= vertices_[iHighest];
         //#endif
         vertices_[iHighest] = pTry;
     }
     return vTry;
 }
コード例 #19
0
        public override void update()
        {
            coeff_.updateModelInstance();

            // we should also check that y contains positive values only

            // we must update weights if it is vegaWeighted
            if (vegaWeighted_)
            {
                coeff_.weights_.Clear();
                double weightsSum = 0.0;

                for (int i = 0; i < xBegin_.Count; i++)
                {
                    double stdDev = Math.Sqrt((yBegin_[i]) * (yBegin_[i]) * coeff_.t_);
                    coeff_.weights_.Add(coeff_.model_.weight(xBegin_[i], forward_, stdDev, coeff_.addParams_));
                    weightsSum += coeff_.weights_.Last();
                }

                // weight normalization
                for (int i = 0; i < coeff_.weights_.Count; i++)
                {
                    coeff_.weights_[i] /= weightsSum;
                }
            }

            // there is nothing to optimize
            if (coeff_.paramIsFixed_.Aggregate((a, b) => b && a))
            {
                coeff_.error_           = interpolationError();
                coeff_.maxError_        = interpolationMaxError();
                coeff_.XABREndCriteria_ = EndCriteria.Type.None;
                return;
            }

            XABRError costFunction = new XABRError(this);

            Vector guess = new Vector(coeff_.model_.dimension());

            for (int i = 0; i < guess.size(); ++i)
            {
                guess[i] = coeff_.params_[i].GetValueOrDefault();
            }

            int    iterations     = 0;
            int    freeParameters = 0;
            double bestError      = double.MaxValue;
            Vector bestParameters = new Vector();

            for (int i = 0; i < coeff_.model_.dimension(); ++i)
            {
                if (!coeff_.paramIsFixed_[i])
                {
                    ++freeParameters;
                }
            }
            HaltonRsg halton = new HaltonRsg(freeParameters, 42);

            EndCriteria.Type tmpEndCriteria;
            double           tmpInterpolationError;

            do
            {
                if (iterations > 0)
                {
                    Sample <List <double> > s = halton.nextSequence();
                    coeff_.model_.guess(guess, coeff_.paramIsFixed_, forward_, coeff_.t_, s.value, coeff_.addParams_);
                    for (int i = 0; i < coeff_.paramIsFixed_.Count; ++i)
                    {
                        if (coeff_.paramIsFixed_[i])
                        {
                            guess[i] = coeff_.params_[i].GetValueOrDefault();
                        }
                    }
                }

                Vector inversedTransformatedGuess =
                    new Vector(coeff_.model_.inverse(guess, coeff_.paramIsFixed_, coeff_.params_, forward_));

                ProjectedCostFunction rainedXABRError = new ProjectedCostFunction(costFunction,
                                                                                  inversedTransformatedGuess,
                                                                                  coeff_.paramIsFixed_);

                Vector projectedGuess = new Vector(rainedXABRError.project(inversedTransformatedGuess));

                constraint_.config(rainedXABRError, coeff_, forward_);
                Problem problem = new Problem(rainedXABRError, constraint_, projectedGuess);
                tmpEndCriteria = optMethod_.minimize(problem, endCriteria_);
                Vector projectedResult = new Vector(problem.currentValue());
                Vector transfResult    = new Vector(rainedXABRError.include(projectedResult));
                Vector result          = coeff_.model_.direct(transfResult, coeff_.paramIsFixed_, coeff_.params_, forward_);
                tmpInterpolationError = useMaxError_
                                    ? interpolationMaxError()
                                    : interpolationError();

                if (tmpInterpolationError < bestError)
                {
                    bestError               = tmpInterpolationError;
                    bestParameters          = result;
                    coeff_.XABREndCriteria_ = tmpEndCriteria;
                }
            }while (++iterations < maxGuesses_ &&
                    tmpInterpolationError > errorAccept_);

            for (int i = 0; i < bestParameters.size(); ++i)
            {
                coeff_.params_[i] = bestParameters[i];
            }

            coeff_.error_    = interpolationError();
            coeff_.maxError_ = interpolationMaxError();
        }
コード例 #20
0
ファイル: T_Optimizers.cs プロジェクト: akasolace/qlnet
 public override Vector values(Vector x)
 {
     // dummy nested optimization
     Vector coefficients = new Vector(3, 1.0);
     OneDimensionalPolynomialDegreeN oneDimensionalPolynomialDegreeN = new OneDimensionalPolynomialDegreeN(coefficients);
     NoConstraint constraint = new NoConstraint();
     Vector initialValues = new Vector(1, 100.0);
     Problem problem = new Problem(oneDimensionalPolynomialDegreeN, constraint, initialValues);
     LevenbergMarquardt optimizationMethod = new LevenbergMarquardt();
     //Simplex optimizationMethod(0.1);
     //ConjugateGradient optimizationMethod;
     //SteepestDescent optimizationMethod;
     EndCriteria endCriteria = new EndCriteria(1000, 100, 1e-5, 1e-5, 1e-5);
     optimizationMethod.minimize(problem, endCriteria);
     // return dummy result
     Vector dummy = new Vector(1,0);
     return dummy;
 }
コード例 #21
0
ファイル: LineSearch.cs プロジェクト: vdt/QLNet
 //! Perform line search
 public abstract double value(Problem P, ref EndCriteria.Type ecType, EndCriteria NamelessParameter3, double t_ini);
コード例 #22
0
ファイル: T_Optimizers.cs プロジェクト: akasolace/qlnet
        public void OptimizersTest()
        {
            //("Testing optimizers...");

            setup();

            // Loop over problems (currently there is only 1 problem)
            for (int i=0; i<costFunctions_.Count; ++i) {
                Problem problem = new Problem(costFunctions_[i], constraints_[i], initialValues_[i]);
                Vector initialValues = problem.currentValue();
                // Loop over optimizers
                for (int j = 0; j < (optimizationMethods_[i]).Count; ++j) {
                    double rootEpsilon = endCriterias_[i].rootEpsilon();
                    int endCriteriaTests = 1;
                   // Loop over rootEpsilon
                    for(int k=0; k<endCriteriaTests; ++k) {
                        problem.setCurrentValue(initialValues);
                        EndCriteria endCriteria = new EndCriteria(endCriterias_[i].maxIterations(),
                                                                  endCriterias_[i].maxStationaryStateIterations(),
                                                                  rootEpsilon,
                                                                  endCriterias_[i].functionEpsilon(),
                                                                  endCriterias_[i].gradientNormEpsilon());
                        rootEpsilon *= .1;
                        EndCriteria.Type endCriteriaResult =
                            optimizationMethods_[i][j].optimizationMethod.minimize(problem, endCriteria);
                        Vector xMinCalculated = problem.currentValue();
                        Vector yMinCalculated = problem.values(xMinCalculated);
                        // Check optimization results vs known solution
                        if (endCriteriaResult==EndCriteria.Type.None ||
                            endCriteriaResult==EndCriteria.Type.MaxIterations ||
                            endCriteriaResult==EndCriteria.Type.Unknown)
                            Assert.Fail("function evaluations: " + problem.functionEvaluation()  +
                                      " gradient evaluations: " + problem.gradientEvaluation() +
                                      " x expected:           " + xMinExpected_[i] +
                                      " x calculated:         " + xMinCalculated +
                                      " x difference:         " + (xMinExpected_[i]- xMinCalculated) +
                                      " rootEpsilon:          " + endCriteria.rootEpsilon() +
                                      " y expected:           " + yMinExpected_[i] +
                                      " y calculated:         " + yMinCalculated +
                                      " y difference:         " + (yMinExpected_[i]- yMinCalculated) +
                                      " functionEpsilon:      " + endCriteria.functionEpsilon() +
                                      " endCriteriaResult:    " + endCriteriaResult);
                    }
                }
            }
        }
コード例 #23
0
        //! Solve least square problem using numerix solver
        public Vector perform(ref LeastSquareProblem lsProblem)
        {
            double eps = accuracy_;

            // wrap the least square problem in an optimization function
            LeastSquareFunction lsf = new LeastSquareFunction(lsProblem);

            // define optimization problem
            Problem P = new Problem(lsf, c_, initialValue_);

            // minimize
            EndCriteria ec = new EndCriteria(maxIterations_, Math.Min((int)(maxIterations_ / 2), (int)(100)), eps, eps, eps);
            exitFlag_ = (int)om_.minimize(P, ec);

            // summarize results of minimization
            //        nbIterations_ = om_->iterationNumber();

            results_ = P.currentValue();
            resnorm_ = P.functionValue();
            bestAccuracy_ = P.functionValue();

            return results_;
        }
コード例 #24
0
ファイル: model.cs プロジェクト: ammachado/QLNet
        //! Calibrate to a set of market instruments (caps/swaptions)
        /*! An additional constraint can be passed which must be
            satisfied in addition to the constraints of the model.
        */
        //public void calibrate(List<CalibrationHelper> instruments, OptimizationMethod method, EndCriteria endCriteria,
        //           Constraint constraint = new Constraint(), List<double> weights = new List<double>()) {
        public void calibrate(List<CalibrationHelper> instruments, OptimizationMethod method, EndCriteria endCriteria,
            Constraint additionalConstraint, List<double> weights)
        {
            if (!(weights.Count == 0 || weights.Count == instruments.Count))
                throw new ApplicationException("mismatch between number of instruments and weights");

            Constraint c;
            if (additionalConstraint.empty())
                c = constraint_;
            else
                c = new CompositeConstraint(constraint_,additionalConstraint);
            List<double> w = weights.Count == 0 ? new InitializedList<double>(instruments.Count, 1.0): weights;
            CalibrationFunction f = new CalibrationFunction(this, instruments, w);

            Problem prob = new Problem(f, c, parameters());
            shortRateEndCriteria_ = method.minimize(prob, endCriteria);
            Vector result = new Vector(prob.currentValue());
            setParams(result);
            // recheck
            Vector shortRateProblemValues_ = prob.values(result);

            notifyObservers();
        }
コード例 #25
0
ファイル: Simplex.cs プロジェクト: tzhdingli/qlnet
        public override EndCriteria.Type minimize(Problem P, EndCriteria endCriteria)
        {
            // set up of the problem
            //double ftol = endCriteria.functionEpsilon();    // end criteria on f(x) (see Numerical Recipes in C++, p.410)
            double xtol = endCriteria.rootEpsilon(); // end criteria on x (see GSL v. 1.9, http://www.gnu.org/software/gsl/)
            int    maxStationaryStateIterations_ = endCriteria.maxStationaryStateIterations();

            EndCriteria.Type ecType = EndCriteria.Type.None;
            P.reset();
            Vector x_ = P.currentValue();
            int    iterationNumber_ = 0;

            // Initialize vertices of the simplex
            bool end = false;
            int  n   = x_.Count;

            vertices_ = new InitializedList <Vector>(n + 1, x_);
            for (int i = 0; i < n; i++)
            {
                Vector direction = new Vector(n, 0.0);
                Vector vertice   = vertices_[i + 1];
                direction[i] = 1.0;
                P.constraint().update(ref vertice, direction, lambda_);
                vertices_[i + 1] = vertice;
            }
            // Initialize function values at the vertices of the simplex
            values_ = new Vector(n + 1, 0.0);
            for (int i = 0; i <= n; i++)
            {
                values_[i] = P.value(vertices_[i]);
            }
            // Loop looking for minimum
            do
            {
                sum_ = new Vector(n, 0.0);
                for (int i = 0; i <= n; i++)
                {
                    sum_ += vertices_[i];
                }
                // Determine the best (iLowest), worst (iHighest)
                // and 2nd worst (iNextHighest) vertices
                int iLowest = 0;
                int iHighest;
                int iNextHighest;
                if (values_[0] < values_[1])
                {
                    iHighest     = 1;
                    iNextHighest = 0;
                }
                else
                {
                    iHighest     = 0;
                    iNextHighest = 1;
                }
                for (int i = 1; i <= n; i++)
                {
                    if (values_[i] > values_[iHighest])
                    {
                        iNextHighest = iHighest;
                        iHighest     = i;
                    }
                    else
                    {
                        if ((values_[i] > values_[iNextHighest]) && i != iHighest)
                        {
                            iNextHighest = i;
                        }
                    }
                    if (values_[i] < values_[iLowest])
                    {
                        iLowest = i;
                    }
                }
                // Now compute accuracy, update iteration number and check end criteria
                //// Numerical Recipes exit strategy on fx (see NR in C++, p.410)
                //double low = values_[iLowest];
                //double high = values_[iHighest];
                //double rtol = 2.0*std::fabs(high - low)/
                //    (std::fabs(high) + std::fabs(low) + QL_EPSILON);
                //++iterationNumber_;
                //if (rtol < ftol ||
                //    endCriteria.checkMaxIterations(iterationNumber_, ecType)) {
                // GSL exit strategy on x (see GSL v. 1.9, http://www.gnu.org/software/gsl
                double simplexSize = Utils.computeSimplexSize(vertices_);
                ++iterationNumber_;
                if (simplexSize < xtol || endCriteria.checkMaxIterations(iterationNumber_, ref ecType))
                {
                    endCriteria.checkStationaryPoint(0.0, 0.0, ref maxStationaryStateIterations_, ref ecType);
                    endCriteria.checkMaxIterations(iterationNumber_, ref ecType);
                    x_ = vertices_[iLowest];
                    double low = values_[iLowest];
                    P.setFunctionValue(low);
                    P.setCurrentValue(x_);
                    return(ecType);
                }
                // If end criteria is not met, continue
                double factor = -1.0;
                double vTry   = extrapolate(ref P, iHighest, ref factor);
                if ((vTry <= values_[iLowest]) && (factor == -1.0))
                {
                    factor = 2.0;
                    extrapolate(ref P, iHighest, ref factor);
                }
                else if (Math.Abs(factor) > Const.QL_EPSILON)
                {
                    if (vTry >= values_[iNextHighest])
                    {
                        double vSave = values_[iHighest];
                        factor = 0.5;
                        vTry   = extrapolate(ref P, iHighest, ref factor);
                        if (vTry >= vSave && Math.Abs(factor) > Const.QL_EPSILON)
                        {
                            for (int i = 0; i <= n; i++)
                            {
                                if (i != iLowest)
                                {
#if QL_ARRAY_EXPRESSIONS
                                    vertices_[i] = 0.5 * (vertices_[i] + vertices_[iLowest]);
#else
                                    vertices_[i] += vertices_[iLowest];
                                    vertices_[i] *= 0.5;
#endif
                                    values_[i] = P.value(vertices_[i]);
                                }
                            }
                        }
                    }
                }
                // If can't extrapolate given the constraints, exit
                if (Math.Abs(factor) <= Const.QL_EPSILON)
                {
                    x_ = vertices_[iLowest];
                    double low = values_[iLowest];
                    P.setFunctionValue(low);
                    P.setCurrentValue(x_);
                    return(EndCriteria.Type.StationaryFunctionValue);
                }
            } while (end == false);
            throw new ApplicationException("optimization failed: unexpected behaviour");
        }