|
Boost Users : |
From: Ares Lagae (ares.lagae_at_[hidden])
Date: 2007-05-30 09:24:02
With the help of the boost lists I finally solved the problem of callbacks
to a function template. I will describe what exactly the problem was, and
how I have solved it, in the hope that it will be usefull for somebody. I
am also open for suggestions and comments.
Problem description
-------------------
I am building a set of parsers. The parser classes pass data to the
application using callbacks. Because there are potentially a lot of
callbacks, and some of the callbacks are optional, I wrap each callback
into a std::tr1::function object, and then pass it to the parser.
The problem I came across can be simplified and abstracted to parsing a
format like this one.
bool 1
char 2
short 3
int 4
long 5
float 6.0
double 7.0
Each line contains a type and is followed by a value of that type. This data
should be parsed and passed to the application. The types are fixed (bool,
char, short, int, long, float, double). (In the actual real problem, there
are more types, and "declarations" involving several types.)
Solution 1
----------
The first solution (see listing_1.cpp) registers a callback for each data
type. Because each data type is handled in a similar way, there is a lot of
code repetition.
Solution 2
----------
The second solution (see listing_2.cpp and variable_list.hpp) replaces the
callback function by a function template. Instead of having a member
variable for the callback for each data type, the member variables are
grouped into a "variable_list". This is a class template that, for each
type in a type list, keeps a variable.
The code repetition in the parser class is eliminated, but the user still
has to call "set_callback" to register a callback for each of the data
types.
Solution 3
----------
The third solution (see listing_3.cpp) eliminates the similar code at the
user side. Instead of calling "set_callback" to register a callback for
each of the data types, a functor is constructed, that for each type
constructs a std::tr1::function object that wraps the callback. That
function object is passed to the parser, and the parser sets all the
callbacks. This again results in similar code in the
parser "set_callbacks".
Solution 4
----------
The fourth solution (see listing_4.cpp) eliminates the similar code in the
parser "set_callbacks" by executing a functor for each type in the type
list. This code is approximately equivalent to callbacks to a function
template.
Best regards,
-- Ares Lagae Computer Graphics Research Group, Katholieke Universiteit Leuven http://www.cs.kuleuven.be/~ares/
Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net