|
Boost : |
Subject: Re: [boost] [Opaque] Request for interest in Opaque typedefs library emulation
From: Fernando Pelliccioni (fpelliccioni_at_[hidden])
Date: 2011-07-20 13:23:48
Hi Vicente,
On Wed, Jul 20, 2011 at 12:56 PM, Vicente Botet <vicente.botet_at_[hidden]>wrote:
>
> Fernando Pelliccioni wrote:
> >
> > On Thu, May 6, 2010 at 2:07 PM, vicente.botet
> > <vicente.botet_at_[hidden]>wrote:
> >
> >> Hi,
> >>
> >> I have started to play with a class to define opaque typedefs on
> >> funcdamental types. It is based on the C++ proposal "
> >> Progress toward Opaque Typedefs for C++0X" by Walter E. Brown
> >> http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2005/n1891.pdf
> >> and http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2004/n1706.pdf
> >>
> >> Please take a look on the preceding links to understand the motivation.
> >>
> >> Boost.Sericalization provide a BOOST_STRONG_TYPEDEF already, but in my
> >> opinon the implementation is not complete,as only the order operators
> are
> >> defined (But maybe I'm wrong).
> >>
> >> Evidently it can not provide everything we can have with a language
> >> approach, but IMO this could yet be useful.
> >>
> >> The library include two class templates (CRTP) to define opaque types:
> >> * public_opaque_type<OT,UT> : implicit conversion from OT to UT
> >> * private_opaque_type<OT,UT> : no conversion from OT to UT
> >>
> >> An opaque type (OT) is a new type, different from the underlying type
> >> (UT)
> >> and other OT. It defines explicit constructor from the UT, and defines
> >> all
> >> the operators the UT support but this time applied to the OT.
> >>
> >> To define a new OT with this mixin classes
> >>
> >> struct serial_number: public_opaque_type<serial_number, unsigned>
> >> {
> >> BOOST_OPAQUE_PUPLIC_FORWARD_CONSTRUCTORS(serial_number,unsigned);
> >> };
> >>
> >> struct game_score: private_opaque_type<game_score, unsigned>
> >> {
> >> BOOST_OPAQUE_PRIVATE_FORWARD_CONSTRUCTORS(game_score,unsigned);
> >> };
> >>
> >> In addition, defines macros that make this simpler
> >>
> >> BOOST_OPAQUE_PUBLIC_TYPEDEF(unsigned, serial_number);
> >> BOOST_OPAQUE_PRIVATE_TYPEDEF(unsigned, game_score);
> >>
> >>
> >> Next follows the definition of the public_opaque_type
> >>
> >> template <typename Final, typename T>
> >> class public_opaque_type
> >> : boost::totally_ordered< Final
> >> , boost::integer_arithmetic< Final
> >> , boost::bitwise< Final
> >> , boost::unit_steppable< Final
> >> , boost::totally_ordered< T, Final // public specific
> conversions
> >> , boost::integer_arithmetic< T, Final // public specific
> >> conversions
> >> , boost::bitwise< T, Final // public specific conversions
> >> > > > > > > >
> >> {
> >> protected:
> >> T val_;
> >> typedef public_opaque_type opaque_type;
> >> public:
> >> typedef T underlying_type;
> >> explicit public_opaque_type(const T v)
> >> : val_(v) {};
> >> public_opaque_type() {};
> >> public_opaque_type(const opaque_type & rhs)
> >> : val_(rhs.val_) {}
> >> public_opaque_type & operator=(const opaque_type & rhs) {
> >> val_ = rhs.val_; return *this;
> >> }
> >> public_opaque_type & operator=(const T rhs) {
> >> val_ = rhs; return *this;
> >> }
> >> T const& underlying() const {
> >> return val_;
> >> }
> >> T& underlying() {
> >> return val_;
> >> }
> >> operator const T & () const {
> >> return val_;
> >> }
> >> operator T & () {
> >> return val_;
> >> }
> >> #if 0
> >> bool operator==(const opaque_type & rhs) const {
> >> return val_ == rhs.val_;
> >> }
> >> #endif
> >> bool operator<(const Final & rhs) const {
> >> return val_ < rhs.val_;
> >> }
> >> Final& operator+=(const Final & rhs) {
> >> val_ += rhs.val_;
> >> return static_cast<Final&>(*this);
> >> }
> >> Final& operator-=(const Final & rhs) {
> >> val_ -= rhs.val_;
> >> return static_cast<Final&>(*this);
> >> }
> >> ...
> >> };
> >>
> >> I have started to make some tests and it works well for the moment.
> >>
> >> Limitations:
> >>
> >> * As we can not specialize the behaviour of static_cast/dynamic_cast the
> >> library sould provide two specific casts opaque_static_cast and
> >> opaque_dynamic_static_cast (Not yet implemented).
> >> * As operator.() can not be overloaded, it works transparently only for
> >> underlying types that don't defines member functions (C++ fundamental
> >> types,
> >> as int, char, ...). For the others an explicit use of the underlying()
> >> member function is needed :(
> >> * Others I have not catched yet :(
> >>
> >> Do you think it is worth continuing?
> >>
> >> Please, let me know if you see a error on the design.
> >>
> >
> >
> > Hi Vicente,
> >
> > I am testing Boost.Opaque.
> > I am using Boost 1.47 + Boost.Conversion + Boost.Opaque ( both from the
> > sandbox ). GCC 4.4 on Linux
> >
> > When I include
> >
> >
> > #include <boost/opaque.hpp>
> >
> >
> > ... I get compilation errors ...
> >
> > boost/opaque/meta_mixin/using_explicit_conversion_to_ut_hierarchy.hpp:81:
> > error: boost::dummy has not been declared
> > boost/opaque/meta_mixin/using_explicit_conversion_to_ut_hierarchy.hpp:81:
> > error: expected , or ... before < token
> >
> >
> > I miss something?
> >
> >
>
> Hi,
>
> I guess that my last changes on Boost.Conversions are the cause.
> I forgot to adapt Boost.Opaque to the new interface. I will do it today or
> tomorrow.
>
Don't worry, take your time.
>
> Thanks for catching it,
>
not at all
Regards,
Fernando.
Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk