|
Boost : |
From: Joaquín Mª López Muñoz (joaquin_at_[hidden])
Date: 2008-02-04 08:32:13
Robert Ramey ha escrito:
> "JOAQUIN LOPEZ MU?Z" wrote:
> > Hello Robert,
> >
> > ----- Mensaje original -----
> > De: Robert Ramey <ramey_at_[hidden]>
> > Fecha: Domingo, Febrero 3, 2008 8:01 pm
> > Asunto: [boost] question about flyweight
> > Para: boost_at_[hidden]
[...]
> >> b) I'm curious about the serialization implementation. Why didn't
> >> you choose just to serialize the factory? This seems to me the most
> >> obvious implementation and I wonder why you didn't feel it was
> >> a good choice.
> > [...]
> >> In short, I don't see why a "helper" is required.
> >
> > Details aside, it all boils down to this:
> >
> > ar << f.h;
> >
> > This only works off the shelf if f.h is a pointer, which is not
> > the case in general (the type of this handle is provided
> > by the particular factory used, and need not be a pointer,
> > for instance in set_factroy is a std::set::iterator).
> > Briefly put, the serialization helper used by flyweight mimics
> > for handle_type the tracking facilities Boost.Serialization
> > provides natively for pointers.
>
> The default is to track if and only if its serialized through a pointer.
>
> If the tracking level serialization trait for flyweight<T> is set to
> track_always it should work
> with all objects.
>
> I would think that you could get the effect you intend by just setting
> this serialization trait.for these types.
I can do something of sorts, but it's not as efficient as with the aid of a
helper: Suppose T is tracked, then your proposed approach would be
something like this:
template<
class Archive,
typename T,typename Arg1,typename Arg2,typename Arg3
>
void save(
Archive& ar,const ::boost::flyweights::flyweight<T,Arg1,Arg2,Arg3>& f,
const unsigned int version)
{
typedef ::boost::flyweights::flyweight<T,Arg1,Arg2,Arg3> flyweight;
ar << &f.get();
}
template<
class Archive,
typename T,typename Arg1,typename Arg2,typename Arg3
>
void load(
Archive& ar,const ::boost::flyweights::flyweight<T,Arg1,Arg2,Arg3>& f,
const unsigned int version)
{
typedef ::boost::flyweights::flyweight<T,Arg1,Arg2,Arg3> flyweight;
T* p;
ar >> p;
f=*p; // HERE
if(&f.get()!=p){
ar.reset_object_address(&f.get(),p);
delete p;
}
}
The problem is with the line marked //HERE : we are incurring a lookup
operation for each duplicate flyweight, while this is avoided when a helper is
used. As a matter of fact, I measured this approach against the helper
implementation and the performance of the latter is easily 2x or 3x better
(I don't remember the exact figures, I can retest if you're interested.)
Joaquín M López Muñoz
Telefónica, Investigación y Desarrollo
Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk