1

I finally got the formula for the distance from a curve to a point running: approx = 2 * (b * (Math.Log(a) * (Math.Log(k) * Math.Pow(k, (b * cycleX))) * Math.Pow(a, (Math.Pow(k, (b * cycleX)))) * (Math.Pow(a, (Math.Pow(k, (b * cycleX))))) - points[i].Y) + cycleX - points[i].X);

So, as approx goes closer to 0, the cycleX gives me the right coordinate from which to calculate the distance to the point.

The only issue here is defining a way to modify cycleX. I tried using a series of if's, but with them sometimes approx ends up jumping on to positive numbers (coming from negatives). What should I do to get the right modification to the value of cycleX?

Note: It usually needs to come down to 0.0001 to get something within the range of -1 to 1.

OFRBG
  • 1,653
  • 14
  • 28
  • I'm confused what's being asked here. – JayC Feb 01 '13 at 05:26
  • Ok... it seems to be related to http://stackoverflow.com/questions/14531309/shortest-distance-from-a-point-to-this-curve, it's accepted answer, and finding a zero for it (that is, find the cycleX that makes approx == 0). – JayC Feb 02 '13 at 21:39

1 Answers1

0

For this kind of problem, it's often useful to know about Newton's method:

Of course, the forumula for that is

x_{n+1} = x_n - \frac{f(x_n)}{f'(x_n)}. \,!

Of course, besides the fact that for some functions this quite unstable (I don't expect yours to be, though), implemented purely for your case, it would mean you would need to calculate yet another derivative (of your derivative)! However, I think for your case, you might be able to just approximate the derivative.

You didn't mention the language your implementation would eventually be in, so I'll just use javascript for convenience.

To estimate your derivative, simply choose a deltaX that would be convenient.

So if you have a function

var df = function (cycleX) {
  return 2 * (b * (Math.log(a) * (Math.log(k) * Math.pow(k, (b * cycleX))) * Math.pow(a, (Math.pow(k, (b * cycleX)))) * (Math.pow(a, (Math.pow(k, (b * cycleX))))) - Y) + cycleX - X);
};

you can estimate it's derivative via

  y = df(cycleX);
  y1 = (df(cycleX + deltaX) - y) / deltaX;

And then proceed via.

  cycleXnew = cycleX - y / y1;

And then it's just a matter of looping until it converges (or not).

See example jsFiddle: http://jsfiddle.net/jfcox/3wRtj/

Edit: I give no guarantees as to how fast it might converge or even how well an estimated derivative would work with respect to Newton's method. For the parameters I've tried given your function f(x) = a^(k^(bx)), it seems to work well, but I haven't tried much.

Edit II. Of course, the above jsFiddle also assumes only a single solution that we'd need to search for.

JayC
  • 7,053
  • 2
  • 25
  • 41