Skip to content
This repository has been archived by the owner on Nov 19, 2020. It is now read-only.

Commit

Permalink
#821: Promoting IConstraint's Function and Gradient properties to met…
Browse files Browse the repository at this point in the history
…hods.
  • Loading branch information
CatchemAL committed Oct 11, 2017
1 parent b09adaf commit cb36812
Show file tree
Hide file tree
Showing 3 changed files with 68 additions and 67 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,6 @@

namespace Accord.Math.Optimization
{
using System;

/// <summary>
/// Defines an interface for an optimization constraint.
/// </summary>
Expand Down Expand Up @@ -52,20 +50,24 @@ public interface IConstraint
/// Gets the number of variables in the constraint.
/// </summary>
///
int NumberOfVariables { get; }

/// <summary>
/// Gets the left hand side of
/// the constraint equation.
/// </summary>
///
Func<double[], double> Function { get; }
int NumberOfVariables { get; }

/// <summary>
/// Calculates the left hand side of the constraint
/// equation given a vector x.
/// </summary>
/// <param name="x">The vector.</param>
/// <returns>
/// The left hand side of the constraint equation as evaluated at x.
/// </returns>
double Function(double[] x);

/// <summary>
/// Gets the gradient of the left hand
/// side of the constraint equation.
/// </summary>
///
Func<double[], double[]> Gradient { get; }
/// <summary>
/// Calculates the gradient of the constraint
/// equation given a vector x
/// </summary>
/// <param name="x">The vector.</param>
/// <returns>The gradient of the constraint as evaluated at x.</returns>
double[] Gradient(double[] x);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -170,9 +170,6 @@ public LinearConstraint(int numberOfVariables)
this.indices = Vector.Range(numberOfVariables);
this.combinedAs = Vector.Ones(numberOfVariables);
this.ShouldBe = ConstraintType.GreaterThanOrEqualTo;

this.Function = compute;
this.Gradient = gradient;
}

/// <summary>
Expand All @@ -189,9 +186,6 @@ public LinearConstraint(params double[] coefficients)
this.indices = Vector.Range(0, coefficients.Length);
this.CombinedAs = coefficients;
this.ShouldBe = ConstraintType.GreaterThanOrEqualTo;

this.Function = compute;
this.Gradient = gradient;
}

/// <summary>
Expand All @@ -210,9 +204,6 @@ public LinearConstraint(IObjectiveFunction function, string constraint, CultureI
: this()
{
parseString(function, constraint, format);

this.Function = compute;
this.Gradient = gradient;
}

/// <summary>
Expand Down Expand Up @@ -242,9 +233,6 @@ public LinearConstraint(IObjectiveFunction function, Expression<Func<bool>> cons
: this()
{
parseExpression(function, constraint);

this.Function = compute;
this.Gradient = gradient;
}

/// <summary>
Expand Down Expand Up @@ -298,22 +286,36 @@ public static bool TryParse(string str, CultureInfo culture,
return true;
}

private double compute(double[] input)
/// <summary>
/// Calculates the left hand side of the constraint
/// equation given a vector x.
/// </summary>
/// <param name="x">The vector.</param>
/// <returns>
/// The left hand side of the constraint equation as evaluated at x.
/// </returns>
public double Function(double[] x)
{
double sum = 0;

for (int i = 0; i < indices.Length; i++)
{
double x = input[indices[i]];
int index = indices[i];
double val = x[index];
double a = CombinedAs[i];

sum += x * a;
sum += val * a;
}

return sum;
}

private double[] gradient(double[] x)
/// <summary>
/// Calculates the gradient of the constraint.
/// </summary>
/// <param name="x">The vector.</param>
/// <returns>The gradient of the constraint.</returns>
public double[] Gradient(double[] x)
{
if (grad == null)
{
Expand All @@ -339,7 +341,6 @@ private double[] gradient(double[] x)
return grad;
}


private void parseString(IObjectiveFunction function, string constraint, CultureInfo culture)
{
if (String.IsNullOrEmpty(constraint))
Expand Down Expand Up @@ -634,19 +635,5 @@ private static string parse(Dictionary<string, double> terms, Expression expr, r

return null;
}


/// <summary>
/// Gets the left hand side of the constraint equation.
/// </summary>
///
public Func<double[], double> Function { get; private set; }

/// <summary>
/// Gets the gradient of the left hand side of the constraint equation.
/// </summary>
///
public Func<double[], double[]> Gradient { get; private set; }

}
}
Original file line number Diff line number Diff line change
Expand Up @@ -34,29 +34,18 @@ namespace Accord.Math.Optimization
///
public class NonlinearConstraint : IConstraint, IFormattable
{

private const double DEFAULT_TOL = 1e-8;

private Func<double[], double> function;

private Func<double[], double[]> gradient;

/// <summary>
/// Gets the number of variables in the constraint.
/// </summary>
///
public int NumberOfVariables { get; private set; }

/// <summary>
/// Gets the left hand side of
/// the constraint equation.
/// </summary>
///
public Func<double[], double> Function { get; private set; }

/// <summary>
/// Gets the gradient of the left hand
/// side of the constraint equation.
/// </summary>
///
public Func<double[], double[]> Gradient { get; private set; }

/// <summary>
/// Gets the type of the constraint.
/// </summary>
Expand Down Expand Up @@ -102,14 +91,14 @@ public NonlinearConstraint(IObjectiveFunction objective,

// Generate lambda functions
var func = ExpressionParser.Replace(function, objective.Variables);
this.Function = func.Compile();
this.function = func.Compile();
this.Value = value;
this.Tolerance = withinTolerance;

if (gradient != null)
{
var grad = ExpressionParser.Replace(gradient, objective.Variables);
this.Gradient = grad.Compile();
this.gradient = grad.Compile();

int n = NumberOfVariables;
double[] probe = new double[n];
Expand Down Expand Up @@ -225,6 +214,30 @@ protected NonlinearConstraint()
{
}

/// <summary>
/// Calculates the left hand side of the constraint
/// equation given a vector x.
/// </summary>
/// <param name="x">The vector.</param>
/// <returns>
/// The left hand side of the constraint equation as evaluated at x.
/// </returns>
public double Function(double[] x)
{
return this.function(x);
}

/// <summary>
/// Calculates the gradient of the constraint
/// equation given a vector x
/// </summary>
/// <param name="x">The vector.</param>
/// <returns>The gradient of the constraint as evaluated at x.</returns>
public double[] Gradient(double[] x)
{
return this.gradient(x);
}

/// <summary>
/// Creates a nonlinear constraint.
/// </summary>
Expand All @@ -249,12 +262,11 @@ protected void Create(int numberOfVariables,
this.Value = value;
this.Tolerance = tolerance;

this.Function = function;
this.Gradient = gradient;
this.function = function;
this.gradient = gradient;
}



private static void parse(Expression<Func<double[], bool>> constraint,
out Func<double[], double> function, out ConstraintType shouldBe, out double value)
{
Expand Down

0 comments on commit cb36812

Please sign in to comment.