Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    text
    copied!<p>It is indeed interesting that people ask this over and over again. One reason may be that the proposed solutions are not easy to understand. I for one had problems understanding and implementing them. (the solutions did not work out of the box for me, as you might expect.)</p> <p>With the help of <a href="https://stackoverflow.com/users/423791/tlamadon">tlamadon</a> I just figured out a solution that may be helpful here as well. Let's see what you guys think. </p> <p>So just to recap, the problem is that you have a class that contains a member function on which you want to operate with something from the GSL library. Our example is useful if the GSL interface requires a </p> <pre><code>gsl_function F; </code></pre> <p><a href="http://www.gnu.org/software/gsl/manual/html_node/Providing-the-function-to-solve.html#Providing-the-function-to-solve" rel="nofollow noreferrer">see here for a definition.</a></p> <p>So here is the example class:</p> <pre><code>class MyClass { private: gsl_f_pars *p; // not necessary to have as member public: double obj(double x, void * pars); // objective fun double GetSolution( void ); void setPars( gsl_f_pars * xp ) { p = xp; }; double getC( void ) ; // helper fun }; </code></pre> <p>The objective of this exercise is to be able to </p> <ol> <li>initiate <code>MyClass test</code>, </li> <li>supply it with a paramter struct (or write a corresponding constructor), and</li> <li>call <code>test.GetSolution()</code> on it, which should return whatever the GSL function was used for (the minimum of <code>obj</code>, a root, the integral or whatever)</li> </ol> <p>The trick is now to put have an element in the parameter <code>struct gsl_f_pars</code> which <em>is a pointer to MyClass</em>. Here's the struct:</p> <pre><code>struct gsl_f_pars { double a; double b; double c; MyClass * pt_MyClass; }; </code></pre> <p>The final piece is to provide a wrapper that will be called inside <code>MyClass::GetSolution()</code> (the wrapper is a stand in for the member function <code>MyClass::obj</code>, which we cannot just point to with <code>&amp;obj</code> inside the class). This wrapper will take the parameter struct, dereference <code>pt_MyClass</code> and evaluate <code>pt_MyClass</code>'s member <code>obj</code>: </p> <pre><code>// Wrapper that points to member function // Trick: MyClass is an element of the gsl_f_pars struct // so we can tease the value of the objective function out // of there. double gslClassWrapper(double x, void * pp) { gsl_f_pars *p = (gsl_f_pars *)pp; return p-&gt;pt_MyClass-&gt;obj(x,p); } </code></pre> <p>The full example is a bit too long to post here, so I put up a gist. It's a <a href="https://gist.github.com/floswald/7103615" rel="nofollow noreferrer">header file</a> and a <a href="https://gist.github.com/floswald/7103639" rel="nofollow noreferrer">cpp file</a>, it should be working wherever you have GSL. Compile and run with </p> <pre><code>g++ MyClass.cpp -lgsl -o test ./test </code></pre>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload