c++functionpointersstd-functionstatic-cast

How can a function that requires another function as a parameter can be used within a class in c++?


I have seen this question in different flavors but it does not really address my issue. Here is the situation, I want to use a library, but one of the functions is extremely complex and requires a void(*func)(std::vector<double> &x,double& func,void* ptr) as an input.

I have a class that holds all the key data members, and naturally the function needed by the external library must be a member function. From my understanding, it is not possible. What are the tricks to bypass that requirement?

Normally, I use std::function and std::bind but I don't think there is a way to convert an std::function to void *, and again I cant change the external library. The use of static function prevents me to have access to key data members.

The signature of the library function is

void minlbfgsoptimize(
    minlbfgsstate &state,
    void (*func)(const real_1d_array &x, double &func, void *ptr),
    void (*rep)(const real_1d_array &x, double func, void *ptr) = NULL,
    void *ptr = NULL);

The full code is in https://github.com/hjkuijf/ALGLIB/blob/master/src/optimization.h


Solution

  • This is a C style callback. That void ptr is going to be passed some pointer you provide.

    Your job is to make that ptr have the state you need.

    In your case, it can be a pointer to your class.

    struct Foo {
      static void callback(std::vector<double> &x,double& f,void* ptr){
        return static_cast<Foo*>(ptr)->callback_impl(x, f);
      }
      void callback_impl(std::vector<double>& x, double&f);
    };
    

    Now when calling you oass this as ptr:

    minlbfgsoptimize(state,Foo::callback, nullptr, this);
    

    where this is a Foo*.

    Static member functions are just functions. And pointers can round-trip through being a void* so long as the in and out types match exactly.