Boost logo

Boost Users :

From: Steven Watanabe (watanabesj_at_[hidden])
Date: 2008-03-25 17:41:30


AMDG

Robert Dailey wrote:
> Hi,
>
> Currently I'm using Boost.Signals to transfer Packet objects to
> subscribers. Right now my Boost.Signal looks like below:
>
> boost::signal<void (Packet const& p)>
>
> Right now Packet is the base class for several other packet types,
> each having the specific data a subscriber needs access to. Of course,
> given this design, the only way to obtain the data is to perform a
> downcast via static_cast or dynamic_cast:
>
> WalkPacket const& wp = static_cast<WalkPacket const&>( p ); // 'p'
> here is a generic Packet object.
>
> This is obviously bad design since it isn't type safe at all. It's
> also repetitive and tedious since each subscriber must duplicate the
> logic to perform the downcast. I'm wondering if there's anything in
> Boost you guys can suggest that I use to make this a little better. I
> would prefer to have a common Signal object that can take differently
> typed Slot objects. For example, I want to pass in a slot that looks
> like: "void (WalkPacket& p)" and have the signal utilize implicit
> conversions or something. Templates aren't even being used here
> because I can't find a way to fit them in, since everything is being
> done at runtime and not compile time.

In this case you want the packets that are not WalkPackets to be ignored?
You could wrap the slots in a class like this: (untested)

template<class F, class T>
struct downcaster {
    typedef boost::remove_reference<T> arg_type;
    downcaster(F f) : f(f) {}
    template<class U>
    void operator()(const U& u) const {
        if(arg_type* arg = dynamic_cast<arg_type*>(&u)) {
            f(*arg);
        }
    }
    F f;
};
template<class T, class F>
downcaster<F, T> make_downcaster(F f) {
    return(downcaster<F, T>(f));
}

In Christ,
Steven Watanabe


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