running unknow methods

Hi,
I have a object with 'function attribute' - void (*function1)(CString);
Another object have a function what i want to call from first object.
I made code like this, but if the called method is member of some object this syntax doesnt work. How can I write it

Thank you

class CRAPIFunc
{
    void (*function1)(CString);
    void runMethod(void)
};

CRAPIFunc::runMethod(void)
{
    function1(); // run unknow method !!!!!!!!!!!!!!!!!!!!!!!
}
//---------------------------------
class AnotherObject
{
   void FunctionToRun(void);
   void assoc(void);
}

AnotherObject::FunctionToRUN(void)
{
    //some code
}

AnotherObject::assoc(void)
{
    CRAPIFunc myObject;
    myObject.function1 = &this->FunctionToRun
}




Answer this question

running unknow methods

  • Matthew Stoecker

    If you want to call a member function of an object via a pointer you have to provide a pointer to a member function plus a pointer to the object.

    The syntax for doing this is not nice. Have a look into a C++ textbook and look for pointers-to-member-functions.

    A more elegant way is to use the boost library (www.boost.org). The code could look like this:


    #include <boost\function.hpp>
    #include <boost\bind.hpp>

    typedef boost::function<void (void)> FunctionType;

    class CRAPIFunc
    {
    public:
       FunctionType function1;
       void runMethod(void);
    };

    void CRAPIFunc::runMethod(void)
    {
       function1();
    }

    class AnotherObject
    {
    public:
       void FunctionToRun(void);
       void assoc(void);
    };

    void AnotherObject::FunctionToRun(void)
    {
    }

    void AnotherObject::assoc(void)
    {
       CRAPIFunc myObject;

       /* bind the member function and the 
          object pointer to the function object */

       myObject.function1 =
             boost::bind(&AnotherObject::FunctionToRun,
    this);

       /* will call this->FunctionToRun() */

       myObject.runMethod();

    }


     



    Bernd


  • Toomy Ling

    Hmm...

    Originally I used VS 2005. But I copied and pasted the code into a new Win32 console application in VS 2003, added the include path to the boost libraries and it compiled without any errors. I am using boost 1.31.0.

    Bernd

  • justme2005

    First answer doesn`t work in C++ VS2003... it raise an error "C2091 function return function" but it look very nice and easy.


  • GGavars

    Second answer look very hard :)
    And there are two object which one is inherited from another. And I want to create independent "pointer to member function" in one class to function of another class.
    I am no so clear about your code :(



  • Jillaint

    Another implementation/example that doesn't use boost.



    #include
    <string>
    using namespace std;
    //-- Impl ---------------------------------------------------------------
    //
    // implements the invocation of a bound member function. We use a template,
    // since the member function must be bound to a class known at compile time.
    //
    template <class _Class>
    class RAPIImpl
    {
    public:
       //
       // create a new type that uses pointer-to-member decl syntax
       //
       typedef
    void (_Class::*BoundMemberFunction)(int arg1, const string& arg2);
       RAPIImpl()
       {
       }

       //
       // Use an abstract function as a way to bind to the actual function 
       // being invoked 
       // 
       virtual
    BoundMemberFunction GetBoundMemberFunction() = 0;
       void Invoke( int arg1, const string& arg2 )
       {
          _Class::BoundMemberFunction func = GetBoundMemberFunction();
          // pointer-to-member call syntax using ->* operator, 
          // note downcast from RAPIImpl _Class*
          (((_Class*)this)->*func)( arg1, arg2 ); 
       }
    };
    //-- Example -------------------------------------------------------------
    class TrueLove : public RAPIImpl<TrueLove>
    {
    public:
       TrueLove()
       {
       }
       BoundMemberFunction GetBoundMemberFunction()
       {
         
    return &TrueLove::FunctionToRun; // a pointer-to-member expression
       }

    private:
       void FunctionToRun( int arg1, const string& arg2 )
       {
          printf(
    "On the %dth day of Christmas, my true love sent to me %d %s\n"
             arg1,arg1, arg2.c_str() );
       }
    };

    void
    main()
    {
       TrueLove trueLove;
    // some arbitrary object
       trueLove.Invoke( 12, "drummers drumming" );
       trueLove.Invoke( 11,
    "pipers piping" );
       trueLove.Invoke( 10,
    "lords a-leaping" );
       trueLove.Invoke( 9,
    "ladies dancing" );
       trueLove.Invoke( 8,
    "maids a-milking" );
       trueLove.Invoke( 7,
    "swans a-swimming" );
       trueLove.Invoke( 6,
    "geese a-laying" );
       trueLove.Invoke( 5,
    "golden rings" );
       trueLove.Invoke( 4,
    "calling birds" );
       trueLove.Invoke( 3,
    "french hens" );
       trueLove.Invoke( 2,
    "turtle doves" );
       trueLove.Invoke( 1,
    "partridge in a pear tree" );
    }

     


     



  • Bob Bojanic - MSFT

    Yeah, but how you might write your code will be largely dependent on the object heirarchy of your code in particular.  I had to depart from the pattern you give because pointer-to-members require knowledge of the class that is being bound to, and in order to separate the RAPI class from the client code, I introduced the use of a template.

    But, in general, this was simply an example. You can search the web for "pointer-to-member" for other examples.


  • running unknow methods