4711

Reference to member function

Question:

first of all I know that this is not possible in C++. But I hope someone can tell be a workaround for my problem. I have a class which represents a mathematical function:

class myClass: { private: public: myClass() {}; double value(double, double){ /* doing some complicated calculation here */} }; double integrate { /*calc*/ return integral; }; }

In integrate() I want to create a struct with a reference to value(). The struct is defined as follows:

struct gsl_monte_function_struct { double (*f)(double * x_array, size_t dim, void * params); size_t dim; void * params; };

(I need this struct to call the Monte-Carlo integration routines from GSL)

As said before I know that this is forbidden in C++. But is there any possibility to use gsl_monte_function_struct with a member function of myClass? If it is not possible that myClass can integrate itself, is it possible to call gsl_monte_function_struct from outside the class with value() as reference? Thanks in advance!

Answer1:

If understand you corretly, you want a pointer to a member function of myClass. You can achieve this by declaring the member function pointer as:

double (myClass::*value)(double,double)

This function can later be called on an instance as:

(instance.*value)(x,y);

Alternatively you can use std::bind to create a function object which can be called as an ordinary function without having to keep track of the instance on which it is called after the call to std::bind:

auto& value = std::bind(myClass::value, instance); // .... value(x,y);

Answer2:

Ok so far I found two solutions:

1) (General solution) Using an abstract base class which has a static pointer to the current instance and a static function that calls a function of the derived class. The static function can be used with a function pointer.

Example:

struct gsl_monte{ double (*f)(double y); }; class myBase { private: static myBase* instance; public: myBase(){}; static void setInstance(myBase* newOne); virtual double value(double x) =0; static double callValue(double x);//{return value(x);} }; class myClass : public myBase { public: myClass(){}; double value(double x) { return x; }; }; myBase* myBase::instance = new myClass(); double myBase::callValue(double x){return instance->value(x);} void myBase::setInstance(myBase* newOne){instance=newOne;}; double g(double xx) {return xx;}; int main(int argc, char** argv ){ double x[2]; x[0]=1.3; x[1]=1.3; myClass* instance = new myClass(); myBase::setInstance(instance); instance->value(3); std::cout << "Test " << myBase::callValue(5) << std::endl; gsl_monte T; T.f=&myBase::callValue; double (*f)(double y, void*) = &myBase::callValue; }

2) (Solution specific to my problem) Fortunatly the desired function accepts a parameter pointer, which I can use to pass the current object:

#include <iostream> #include <functional> using namespace std::placeholders; struct gsl_monte{ double (*f)(double y, void*); }; class myClass { public: myClass(){}; double value(double x) { return x; }; }; double valueTT(double x, void* param) { return static_cast<myClass*>(param)->value(x); }; int main(int argc, char** argv ){ double x[2]; x[0]=1.3; x[1]=1.3; myClass* instance = new myClass(); instance->value(3); gsl_monte T; T.f=&valueTT; double (*f)(double y, void*) = &valueTT; }

Recommend

  • Using unique_ptr with gsl_vector
  • Generating standalone MEX file with GNU compilers, including libraries
  • Parsing XML from web
  • Resources Exceeded in BigQuery
  • Xcode 4.3.3 can't find any header files
  • Encircle points with shaded blobs
  • Cannot retrieve repository metadata (repomd.xml) for repository: sandbox. Please verify its path and
  • Best Data Structure for this Multithreaded Use Case: Is Intrusive List good?
  • PayPal IPN OPENSSL error:14077410:SSL routines:SSL23_GET_SERVER_HELLO:sslv3 alert handshake failure
  • Modify application instruction in PIN
  • mmap big endian vs. little endian
  • Does using global variables increase or decrease performance, in C code compiled for ARM7?
  • Creating account using accounts-password in meteor
  • Using bitbake is it possible to have a different do_install for a package based on the target image?
  • How to make Firefox handle the result of a POST request with firefox-addon-sdk?
  • Fail SonarQube quality gate when coverage decreases
  • Doctrine: UniqueEntity with Many-to-Many field
  • How to redirect or show a page rather than “Forbidden” when i have directory listings off (htaccess/
  • How to use HTTP Authentication with PHP and then run the entered data against a database?
  • Youtube upload API and cordova / phonegap
  • $this->params returns null in cakephp model
  • Force application to show TaskBar Icon during OnCreate procedure
  • Setting a relative path to sqlite database with Delphi and Firedac
  • mCamera.setpreview{@override onPreviewFrame() } not work
  • Single virtual attribute definition for multiple fields
  • Sending rails errors to rspec output
  • Rails 3, Custom Actions, and HTML request methods
  • Counting Treaps
  • How do I check if System::Collections:ArrayList is empty / nullptr / null?
  • Wrap C++ function using Boost Reflect or another C++ reflection library
  • Excel VBA URLDownloadToFile Error for https Ressource
  • android Navigation Bar hiding and persantage of usable screen overlap
  • Creating a Multidimensional, Associative Array in VBScript
  • Conversion from string “a” to type 'Boolean' is not valid
  • Rails Find when some params will be blank
  • Confusion with PayPal's monthly billing cycle
  • Can't mass-assign protected attributes when import data from csv file
  • Checking variable from a different class in C#
  • failed to connect to specific WiFi in android programmatically
  • How can I use threading to 'tick' a timer to be accessed by other threads?