Pregunta

En el código de abajo (ver comentario):

#include "stdafx.h"

#include <iostream>
using std::cout;

struct Base
{
 void fnc()
 {
  cout << "Base::fnc()";
 }

};

struct Impl
{
 void* data_;
 Impl(void (Base::*fp)())
 {
  fp();//HERE I'M INVOKING IT - I'M DOING SOMETHING WRONG!
 }
};
int _tmain(int argc, _TCHAR* argv[])
{
 return 0;
}  

Error
"Error 1 Error C2064: término no se evalúa a una toma de función 0 argumentos" ¿Por qué no funciona y cómo solucionarlo?

¿Fue útil?

Solución

typedef  int (MyClass::*memberPointer_t)(int);

...

memberPointer_t mb = &MyClass::function;
MyClass* object = getObject();

int returnValue = (object->*mb)(3);

...

Ya que es un puntero a una función miembro, usted debe llamar a un objeto y utilizar el -..> * O * el operador llamarlo

Otros consejos

No funciona porque fp no es un puntero de función, sino un puntero miembro.

¿Cómo solucionarlo es fácil, lo utilizan, ya que se debe utilizar: someinstance.*fp();

El problema es que está llamando a la función como una función libre, cuando no lo es. Es una función miembro, y hay que llamar en el contexto de un objeto:

(obj.*f)();

Boost.Bind ofrece una forma idiomática para hacer frente a esto:

#include<boost/bind.hpp>

// ...
Impl i(boost::bind(&Base::fnc, obj));

Se puede definir el constructor Impl este modo:

#include<boost/function.hpp>

// ...
Impl(boost::function<void ()> fnc)
{
    fnc();  // boost::bind translates it to obj.fnc()
}

Si sólo el objeto Impl sabe lo que se oponga a llamar a la función, a continuación, puede utilizar los marcadores de posición de Boost.Bind:

Impl i(boost::bind(&Base::fnc, boost::_1));

Y el constructor Impl sería entonces similar a

Impl(boost::function<void (Base)> fnc, Base& b)
{
    fnc(b);  // boost::bind translates it to b.fnc()
}

A veces es más prudente utilizar plantillas en el lado que acepta el functor:

template<class Op>
Impl(Op fnc) { ... }

ya continuación, el cliente puede pasar cualquier función miembro, con o sin impulso. Pero el costo es que es posible que tenga más difícil de entender compilador mensajes de error.

Se necesita una base para llamar a la función.

podría estar buscando algo más parecido a bind () y la función <> que le permitirá enlazar una función miembro de instancia y en un funtor que puede ser llamado simplemente como una función.

Se podría beneficiarse de la lectura este respecto FAQ punteros a funciones miembro. En particular, se recomienda encarecidamente a definir una macro para estas llamadas:

#define CALL_MEMBER_FN(object,ptrToMember) ((object).*(ptrToMember))

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top