Beispiel #1
0
        public void AugmentedLagrangianSolverConstructorTest3()
        {
            // min x*y+ y*z
            //
            // s.t.  x^2 - y^2 + z^2 - 2  >= 0
            //       x^2 + y^2 + z^2 - 10 <= 0
            //

            double x = 0, y = 0, z = 0;

            var f = new NonlinearObjectiveFunction(

                function: () => x * y + y * z,

                gradient: () => new[]
            {
                y,         // df/dx
                x + z,     // df/dy
                y,         // df/dz
            }

                );


            var constraints = new List <NonlinearConstraint>();

            constraints.Add(new NonlinearConstraint(f,

                                                    function: () => x * x - y * y + z * z,
                                                    gradient: () => new[] { 2 * x, -2 * y, 2 * z },

                                                    shouldBe: ConstraintType.GreaterThanOrEqualTo, value: 2
                                                    ));

            constraints.Add(new NonlinearConstraint(f,

                                                    function: () => x * x + y * y + z * z,
                                                    gradient: () => new[] { 2 * x, 2 * y, 2 * z },

                                                    shouldBe: ConstraintType.LesserThanOrEqualTo, value: 10
                                                    ));

            var solver = new AugmentedLagrangianSolver(3, constraints);

            solver.Solution[0] = 1;
            solver.Solution[1] = 1;
            solver.Solution[2] = 1;

            double minValue = solver.Minimize(f);

            Assert.AreEqual(-6.9, minValue, 1e-1);
            Assert.AreEqual(+1.73, solver.Solution[0], 1e-2);
            Assert.AreEqual(-2.00, solver.Solution[1], 1e-2);
            Assert.AreEqual(+1.73, solver.Solution[2], 1e-2);

            Assert.IsFalse(Double.IsNaN(minValue));
            Assert.IsFalse(Double.IsNaN(solver.Solution[0]));
            Assert.IsFalse(Double.IsNaN(solver.Solution[1]));
            Assert.IsFalse(Double.IsNaN(solver.Solution[2]));
        }
Beispiel #2
0
        public static double solve(bool isFine, IEnumerable <Constraint> cons)
        {
            var constraints = cons.ToArray();

            // Get the parameters that need solving by selecting "free" ones
            Parameter[] x = constraints.SelectMany(p => p)
                            .Distinct()
                            .Where(p => p.free == true)
                            .ToArray();

            Console.WriteLine("Number of free vars is " + x.Length);

            // Wrap our constraint error function for Accord.NET
            Func <double[], double> objective = args => {
                int i = 0;
                foreach (var arg in args)
                {
                    x [i].Value = arg;
                    i++;
                }
                return(Constraint.calc(constraints));
            };


            var nlConstraints = new List <NonlinearConstraint> ();

            // Finally, we create the non-linear programming solver
            var solver = new AugmentedLagrangianSolver(x.Length, nlConstraints);

            // Copy in the initial conditions
            x.Select(v => v.Value).ToArray().CopyTo(solver.Solution, 0);

            // And attempt to solve the problem
            return(solver.Minimize(LogWrap(objective), LogWrap(Grad(x.Length, objective))));
        }
Beispiel #3
0
        public void AugmentedLagrangianSolverConstructorTest2()
        {
            // min 100(y-x*x)²+(1-x)²
            //
            // s.t.  x >= 0
            //       y >= 0
            //

            var f = new NonlinearObjectiveFunction(2,

                                                   function: (x) => 100 * Math.Pow(x[1] - x[0] * x[0], 2) + Math.Pow(1 - x[0], 2),

                                                   gradient: (x) => new[]
            {
                2.0 * (200.0 * Math.Pow(x[0], 3) - 200.0 * x[0] * x[1] + x[0] - 1),     // df/dx
                200 * (x[1] - x[0] * x[0])                                              // df/dy
            }

                                                   );


            var constraints = new List <NonlinearConstraint>();

            constraints.Add(new NonlinearConstraint(f,

                                                    function: (x) => x[0],
                                                    gradient: (x) => new[] { 1.0, 0.0 },

                                                    shouldBe: ConstraintType.GreaterThanOrEqualTo, value: 0
                                                    ));

            constraints.Add(new NonlinearConstraint(f,

                                                    function: (x) => x[1],
                                                    gradient: (x) => new[] { 0.0, 1.0 },

                                                    shouldBe: ConstraintType.GreaterThanOrEqualTo, value: 0
                                                    ));

            var solver = new AugmentedLagrangianSolver(2, constraints);

            double minValue = solver.Minimize(f);

            Assert.AreEqual(0, minValue, 1e-10);
            Assert.AreEqual(1, solver.Solution[0], 1e-10);
            Assert.AreEqual(1, solver.Solution[1], 1e-10);

            Assert.IsFalse(Double.IsNaN(minValue));
            Assert.IsFalse(Double.IsNaN(solver.Solution[0]));
            Assert.IsFalse(Double.IsNaN(solver.Solution[1]));
        }
Beispiel #4
0
        public void AugmentedLagrangianSolverConstructorTest1()
        {
            Accord.Math.Tools.SetupGenerator(0);

            // min 100(y-x*x)²+(1-x)²
            //
            // s.t.  x <= 0
            //       y <= 0
            //

            var f = new NonlinearObjectiveFunction(2,

                                                   function: (x) => 100 * Math.Pow(x[1] - x[0] * x[0], 2) + Math.Pow(1 - x[0], 2),

                                                   gradient: (x) => new[]
            {
                2.0 * (200.0 * x[0] * x[0] * x[0] - 200.0 * x[0] * x[1] + x[0] - 1), // df/dx
                200 * (x[1] - x[0] * x[0])                                           // df/dy
            }

                                                   );


            var constraints = new List <NonlinearConstraint>();

            constraints.Add(new NonlinearConstraint(f,

                                                    function: (x) => x[0],
                                                    gradient: (x) => new[] { 1.0, 0.0 },

                                                    shouldBe: ConstraintType.LesserThanOrEqualTo, value: 0
                                                    ));

            constraints.Add(new NonlinearConstraint(f,

                                                    function: (x) => x[1],
                                                    gradient: (x) => new[] { 0.0, 1.0 },

                                                    shouldBe: ConstraintType.LesserThanOrEqualTo, value: 0
                                                    ));

            var solver = new AugmentedLagrangianSolver(2, constraints);

            double minValue = solver.Minimize(f);

            Assert.AreEqual(1, minValue, 1e-5);
            Assert.AreEqual(0, solver.Solution[0], 1e-5);
            Assert.AreEqual(0, solver.Solution[1], 1e-5);
        }
Beispiel #5
0
        public void AugmentedLagrangianSolverConstructorTest5()
        {
            // Suppose we would like to minimize the following function:
            //
            //    f(x,y) = min 100(y-x²)²+(1-x)²
            //
            // Subject to the constraints
            //
            //    x >= 0  (x must be positive)
            //    y >= 0  (y must be positive)
            //

            double x = 0, y = 0;


            // First, we create our objective function
            var f = new NonlinearObjectiveFunction(

                // This is the objective function:  f(x,y) = min 100(y-x²)²+(1-x)²
                function: () => 100 * Math.Pow(y - x * x, 2) + Math.Pow(1 - x, 2),

                // The gradient vector:
                gradient: () => new[]
            {
                2 * (200 * Math.Pow(x, 3) - 200 * x * y + x - 1),     // df/dx = 2(200x³-200xy+x-1)
                200 * (y - x * x)                                     // df/dy = 200(y-x²)
            }

                );


            // Now we can start stating the constraints
            var constraints = new List <NonlinearConstraint>();

            // Add the non-negativity constraint for x
            constraints.Add(new NonlinearConstraint(f,

                                                    // 1st constraint: x should be greater than or equal to 0
                                                    function: () => x, shouldBe: ConstraintType.GreaterThanOrEqualTo, value: 0,

                                                    gradient: () => new[] { 1.0, 0.0 }
                                                    ));

            // Add the non-negativity constraint for y
            constraints.Add(new NonlinearConstraint(f,

                                                    // 2nd constraint: y should be greater than or equal to 0
                                                    function: () => y, shouldBe: ConstraintType.GreaterThanOrEqualTo, value: 0,

                                                    gradient: () => new[] { 0.0, 1.0 }
                                                    ));


            // Finally, we create the non-linear programming solver
            var solver = new AugmentedLagrangianSolver(2, constraints);

            // And attempt to solve the problem
            double minValue = solver.Minimize(f);

            Assert.AreEqual(0, minValue, 1e-10);
            Assert.AreEqual(1, solver.Solution[0], 1e-10);
            Assert.AreEqual(1, solver.Solution[1], 1e-10);

            Assert.IsFalse(Double.IsNaN(minValue));
            Assert.IsFalse(Double.IsNaN(solver.Solution[0]));
            Assert.IsFalse(Double.IsNaN(solver.Solution[1]));
        }