0

I'm having difficulty even beginning to solve this problem. All examples that I have found are either too simple or way too complex to digest.

I want to to find the value S given a series of inputs. The function is univariate but non-linear. S will always be between -3 .. 3.

I would like to use the Apache Commons library, as I have had prior experience in other sections of that code.

For each time I want to solve my problem, I know the following information:

    double R     =250.0;
    double om1   =  5.0;
    double om2   = 15.0;
    double th21  = 29.07965;
    double th22  = 29.69008;
    double D_obs = th21 - th22;

The actual values will change between solutions, but they are fixed for any one particular solution.

The value I want to find is:

    double S   = 0.0; 

such that

    double d1     = delta(R,om1,th21,S);
    double d2     = delta(R,om2,th22,S);
    double D_calc = d1 - d2;

have values to make

    double minme = Math.abs(D_obs - D_calc);

a minimum, or alternately, solve

double minme = D_obs - D_calc;

where minme=0.

The function delta is defined as

public static double delta(double R, double om, double th2, double s)
{
    if(Math.abs(s) <= 0.0001) //is the displacement == 0?
    {
        return 0.0;
    }
    else
    {
        return Math.toDegrees((-1*Cos(th2)*s-R*Sin(om)+Sqrt(-1*Math.pow(Cos(th2),2)*Math.pow(s,2)+2*Cos(th2)*Sin(om)*R*s-Math.pow(Cos(om),2)*Math.pow(R,2)+Math.pow(R,2)+2*Math.pow(s,2)))/(Sin(th2)*s));
    }
}

where, for example, Cosis defined elsewhere as Math.cos(Math.toRadians(val))

Where/what can I read/do to get a start on this problem?

masher
  • 3,814
  • 4
  • 31
  • 35
  • This smells to me like you're going to have to use some form of gradient descent algorithm - perhaps [`NonLinearConjugateGradientOptimizer`](http://commons.apache.org/proper/commons-math/javadocs/api-3.6.1/org/apache/commons/math3/optim/nonlinear/scalar/gradient/NonLinearConjugateGradientOptimizer.html). Bad news is that you're going to need to provide a gradient for that to work - differentiating absolute functions is rather a pain... – Boris the Spider Apr 04 '19 at 08:12
  • Documemtation is _poor_ as to how to set this up; [this forum question](http://apache-commons.680414.n4.nabble.com/How-to-use-NonLinearConjugateGradientOptimizer-td4710000.html) provides some hints... – Boris the Spider Apr 04 '19 at 08:14
  • Differentiating absolute functions is why Maple exists. :) – masher Apr 05 '19 at 01:15

1 Answers1

0

I found an answer I could work with: Newton-Raphson method using the Math.Commons library

The key code is

public static void main(String args[])
{
    //setup all variables
    final double R   =(new Double(args[0])).doubleValue(); //=250.0;
    final double om1 =(new Double(args[1])).doubleValue(); //=  5.0;
    final   double om2 =(new Double(args[2])).doubleValue(); //= 15.0;
    final double th21=(new Double(args[3])).doubleValue(); //= 29.07965;
    final double th22=(new Double(args[4])).doubleValue(); //= 29.69008;
    final double D_obs = th21 - th22;

    BisectionSolver solver = new BisectionSolver();

    UnivariateFunction f = new UnivariateFunction()
    {
        public double value(double s) {
            return ((delta(R,om1,th21,s)-delta(R,om2,th22,s)) - (D_obs));
        }
    };

    System.out.printf("The speciment offset is %.3f mm.\n", solver.solve(1000, f, -3, 3));
}
masher
  • 3,814
  • 4
  • 31
  • 35