forum.alglib.net
http://forum.alglib.net/

Create a loop for Levenberg–Marquardt algorithm C#
http://forum.alglib.net/viewtopic.php?f=2&t=4470
Page 1 of 1

Author:  tungnguyen99 [ Thu Jul 14, 2022 6:50 am ]
Post subject:  Create a loop for Levenberg–Marquardt algorithm C#

Hello everyone,

When I use optimization package with minlm, my function fvec change with 1 variable ( this variable I store it in an array, this array have 100 components).
The question is that , is there anyway to create a for loop to use minlmoptimize and automatic change function fvec?

For example, in the first loop, fvec is equal to the first value of array, and the second loop, fvec is equal the second value.
The start ting point of second loop is the result of 1st loop.

I don't want to create 100 fvec method manually!!

Author:  Sergey.Bochkanov [ Thu Jul 14, 2022 8:51 am ]
Post subject:  Re: Create a loop for Levenberg–Marquardt algorithm C#

Hi!

minlmoptimize() function accepts additional parameter which is a System.Object reference in C#, a void* ptr in C++. This parameter is forwarded to your callback "as is", without changes. You can use it to dynamically change behavior of your fvec method, e.g. to tell it to use first variable from array, second one, third one, etc.

E.g. you can create an instance of control structure that tells fvec what to do, and forward a pointer to this structure to fvec using aforementioned mechanism.

Author:  tungnguyen99 [ Thu Jul 14, 2022 1:31 pm ]
Post subject:  Re: Create a loop for Levenberg–Marquardt algorithm C#

Thank you for your fast response.

Howerver, I'm not familiar with the alglib yet. Can you elaborate it more?

Below is my example.
As you can see, the method Getvalue() contains the array. The method fvec1() will get the first 3 of this array, and the next 3 value is for fvec2(), etc.
And the fvec1 and fvec2 are the same template, just different from the value of array.

So, how to create a for loop for calculate the result in Main() which method fvec() can automatic realize the of array's value corresponding with step of the for loop?
I just want to use only 1 fvec, not creating the second one.

Thanks again!

----------------------------------------------------------------------------------------------------
public static double[,] GetValue()
{
double[,] L = { { 806, 806, 806 }, { 607, 607, 607 }, {702, 702, 702} };

return L;
}

public void function_fvec1(double[] p, double[] fi, object obj)
{
// Set static value
double[] a1 = { (-435 * Math.Cos(Math.PI / 6)), (-435 * Math.Sin(Math.PI / 6)), 0 };
double[] a2 = { (435 * Math.Cos(Math.PI / 6)), (-435 * Math.Sin(Math.PI / 6)), 0 };
double[] a3 = { 0, 435, 0 };

// Array of value
double[,] L = GetValue();
double[] l = { L[0, 0], L[0, 1], L[0, 2] };

// This is call back calculation
fi[0] = Math.Pow(a1[0] - p[0] + 35 * Math.Cos(Math.PI / 6), 2) +
Math.Pow(a1[1] - p[1] + 35 * Math.Sin(Math.PI / 6), 2) +
Math.Pow(a1[2] - p[2], 2) -
Math.Pow(l[0], 2);

fi[1] = Math.Pow(a2[0] - p[0] - 35 * Math.Cos(Math.PI / 6), 2) +
Math.Pow(a2[1] - p[0] + 35 * Math.Sin(Math.PI / 6), 2) +
Math.Pow(a2[2] - p[2], 2) -
Math.Pow(l[1], 2);

fi[2] = Math.Pow(a3[0] - p[0], 2) +
Math.Pow(a3[1] - p[1] - 35, 2) +
Math.Pow(a3[2] - p[2], 2) -
Math.Pow(l[2], 2);
}

public void function_fvec2(double[] p, double[] fi, object obj)
{
// Set static value
double[] a1 = { (-435 * Math.Cos(Math.PI / 6)), (-435 * Math.Sin(Math.PI / 6)), 0 };
double[] a2 = { (435 * Math.Cos(Math.PI / 6)), (-435 * Math.Sin(Math.PI / 6)), 0 };
double[] a3 = { 0, 435, 0 };

// Array of value
double[,] L = GetValue();
double[] l = { L[1, 0], L[1, 1], L[1, 2] };

// This is call back calculation
fi[0] = Math.Pow(a1[0] - p[0] + 35 * Math.Cos(Math.PI / 6), 2) +
Math.Pow(a1[1] - p[1] + 35 * Math.Sin(Math.PI / 6), 2) +
Math.Pow(a1[2] - p[2], 2) -
Math.Pow(l[0], 2);

fi[1] = Math.Pow(a2[0] - p[0] - 35 * Math.Cos(Math.PI / 6), 2) +
Math.Pow(a2[1] - p[0] + 35 * Math.Sin(Math.PI / 6), 2) +
Math.Pow(a2[2] - p[2], 2) -
Math.Pow(l[1], 2);

fi[2] = Math.Pow(a3[0] - p[0], 2) +
Math.Pow(a3[1] - p[1] - 35, 2) +
Math.Pow(a3[2] - p[2], 2) -
Math.Pow(l[2], 2);
}

static void Main(string[] args)
{
// Set static value
double[] a1 = { (-435 * Math.Cos(Math.PI / 6)), (-435 * Math.Sin(Math.PI / 6)), 0 };
double[] a2 = { (435 * Math.Cos(Math.PI / 6)), (-435 * Math.Sin(Math.PI / 6)), 0 };
double[] a3 = { 0, 435, 0 };

double[] plow;
double[] phigh;


double[] p = new double[] { 0, 0, -710 };
double[] s = new double[] { 1, 1, 1 };
double epsx = 0.0000000001;
int maxits = 0;
alglib.minlmstate state;

determine_bc(a1, a2, a3, out plow, out phigh);

alglib.minlmcreatev(3, p, 0.0001, out state);
alglib.minlmsetbc(state, plow, phigh);
alglib.minlmsetcond(state, epsx, maxits);
alglib.minlmsetscale(state, s);

// Optimize
alglib.minlmoptimize(state, function_fvec1, null, null);


// Test result
alglib.minlmreport rep;
alglib.minlmresults(state, out p, out rep);
Console.WriteLine("\n This is result: \n {0}", alglib.ap.format(p, 5));

}

Author:  Sergey.Bochkanov [ Sun Jul 17, 2022 11:20 am ]
Post subject:  Re: Create a loop for Levenberg–Marquardt algorithm C#

Hi!

You can replace last parameter in minlpoptimize() by a reference to a function index, e.g. use boxing to convert int to an object reference. And then decide within fvec() what to do, depending on the unboxed value.

Author:  tungnguyen99 [ Mon Jul 18, 2022 3:27 am ]
Post subject:  Re: Create a loop for Levenberg–Marquardt algorithm C#

I get it.

Thank you for support!

Page 1 of 1 All times are UTC
Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group
http://www.phpbb.com/