-1

Like the title. As a new programmer,It is very important to know the mechanism for my project, and what is the difference of using them. Can any guy give me a answer,thank you!

CashCow
  • 30,981
  • 5
  • 61
  • 92
mac.ma
  • 703
  • 2
  • 8
  • 22

6 Answers6

8

A virtual function is one mechanism to provide a callback, but it is not the only mechanism.

The generality of a callback is that you pass in, as a parameter, a method, or an object that invokes a method, that will be called by the function you pass it to, or will be stored by that function to be called later when an event happens.

One way to implement such a mechanism is to pass in a pointer or reference to an object that derives from a base class and implements a virtual function.

Another way is to pass in a function pointer.

Yet another is to pass in an object that has a function pointer, which is what boost functions are - the constructors to boost function (often boost::bind) cleverly construct such an object for you.

In C++11 you will be able to construct an unnamed function on the fly to be passed as a callback. This is usually referred to as a lambda.

A bit more about the mechanism of using a virtual function as a callback. It can look like quite a neat thing to do:

class Handler
{
  public:
   virtual ~Handler() {}
   virtual void process( std::string const& message ) = 0;
};

void getMessage( Handler& handler )
{
    std::string str = getAMessage();
    handler.process( str );
}

Even tidier is to construct Handler this way:

class Handler
{
  public:
    virtual ~Handler() {}
    void process( std::string const& message ) 
    {
       // can log or put in a breakpoint here on debugging
        doProcess( message );
    }

   protected: // or private
       virtual void doProcess( std::string const& message ) = 0;
};

The advantage here is that it is easy to debug into.

It becomes more complex if the lifetime of the Handler object needs to be managed, i.e. the callback happens asynchronously. Then you have to use a shared_ptr<Handler> so that both sides hold a reference, and it will be managed.

One huge advantage you will find by doing this, over a regular callback function, is that the object can hold extra information. The callback itself can only take a fixed number of parameters, and in a callback one will often use a void* and have to cast it to something to get back the extra information. Using the class allows you to hold that information in member variables, as well as allowing the class to retain state after its method was invoked.

The overhead of using this though is that you have to create such abstract classes and then derive classes from it, and you might find yourself doing this rather a lot.

This is where boost function and bind becomes very useful. What you really want is a function with a specific signature to be called, and not to have to create extra classes to handle this callback. It enables you therefore to program this situation much more quickly.

However, it unfortunately does have a downside too. boost functions are far more difficult to be able to debug into. Whilst you do not have to be careful about managing the lifetime of the boost function itself, you do have to be careful about the parameters you pass into it. It will just blindly store them the way you pass them. If you pass in a reference to local variable as a reference-holder (boost::ref) it will indeed store this reference and if it happens to go out of scope before the function is invoked, you may have a hard time locating this bug.

In spite of this though, I would suggest making use of the library feature (note there is also std::function and std::bind, although when lambdas become standard among compilers, there will be far less requirement for them).

CashCow
  • 30,981
  • 5
  • 61
  • 92
3

Callback functions implement inversion of control (an important design pattern). Virtual functions implement polymorphism (a programming paradigm). Fundamentally, they are unrelated, in the sense that they view the code from two different angles. One way of implementing inversion of control is by means of an abstract base class, whose virtual functions become effectively callback functions. Most of the time when one hears the term callback functions, however, it is with regards to API's defined in C, which can't use abstract base classes and virtual functions. In such cases, a free function (usually extern "C") is required; in most cases, this function will receive a void* argument to allow passing data through to it.

James Kanze
  • 150,581
  • 18
  • 184
  • 329
  • extern "C" has to do with name mangling and not a function prototyping. Other than that your answer is fairly good. – CashCow Feb 24 '12 at 11:09
  • @CashCow `extern "C"` specifies the calling conventions, of which name mangling is only a part. Whether a function is `extern "C"` or not is part of its type; if the compiler allows you to pass an `extern "C++"` function as argument to an function requiring `extern "C"`, it is not conform to the standard. Functions like `pthread_create` require the function passed to them to be `extern "C"` (at least with a compiler which enforces the standard). – James Kanze Feb 24 '12 at 11:18
2

Callback functions: Callback functions in c++

http://www.codeguru.com/cpp/cpp/cpp_mfc/callbacks/article.../c10557

Virtual Functions: http://en.wikipedia.org/wiki/Virtual_function

these are the results you get by googling!! there is nothing more to add. I dont think there is any thing other than differences between callback and virtual functions

Community
  • 1
  • 1
Rohit Vipin Mathews
  • 11,629
  • 15
  • 57
  • 112
2

A callback function is one that is referenced from some other part of the program. Think of how you can pass a pointer to an object around - the same can be done with a function. This could be considered a challenging topic for a beginning programmer, however.

A virtual function refers to a function that can be implemented by a child class. Read up on the term polymorphism.

Alex Z
  • 2,500
  • 2
  • 19
  • 23
1

A callback function is a function you pass as a parameter which might get executed somewhere else.

A virtual function is one of the building blocks of polymorphism in C++. It means that calling this method on an object of the base class will call the same method from the upper-most derived class in the inheritance chain.

Luchian Grigore
  • 253,575
  • 64
  • 457
  • 625
1

Callback function is hard to trace, but sometimes it is very useful. Especially when you are designing libraries. Callback function is like asking your user to gives you a function name, and you will call that function under certain condition.

void cbfunc()
{
    printf("called");
}

int main ()
{
     /* function pointer */
    void (*callback)(void);

    /* point to your callback function */
    callback=(void *)cbfunc;

   /* perform callback */
   callback();

   return 0;
}

And virual function means it used to achieve polymorphism by overriding functions.

Sachin Mhetre
  • 4,465
  • 10
  • 43
  • 68