ASPN ActiveState Programmer Network
ActiveState
/ Home / Perl / PHP / Python / Tcl / XSLT /
/ Safari / My ASPN /
Cookbooks | Documentation | Mailing Lists | Modules | News Feeds | Products | User Groups


Recent Messages
List Archives
About the List
List Leaders
Subscription Options

View Subscriptions
Help

View by Topic
ActiveState
.NET Framework
Open Source
Perl
PHP
Python
Tcl
Web Services
XML & XSLT

View by Category
Database
General
SOAP
System Administration
Tools
User Interfaces
Web Programming
XML Programming


MyASPN >> Mail Archive >> boost
boost
RE: [boost] type_traits: workaround bias
by Yitzhak Sapir other posts by this author
Mar 17 2002 12:22PM messages near this date
Threads: New version of rw_lock uploaded to files section | Re: [boost] Re: Design for a file system library
I tried experimenting with this a bit. I think now that essentially
this is the result of the reference/pointer to reference problem. If
you had a solution to that, you could declare all the static T's as T&
and solve the issue.

I have the following code which prints 1 four times and then 0 five
times on MSVC6SP5. Does this solve all potential issues. Am I missing
anything here?

using namespace boost;
using namespace boost::type_traits;

template <class T>  struct type_wrapper{ };

template<class T1>  yes_type is_pointer_helper1(T1*);
no_type is_pointer_helper1(...);
template <class T>  T* is_pointer_helper2(type_wrapper<T>);

template <bool IsPointerOrReference>  struct is_pointer_class_helper;
template <>  struct is_pointer_class_helper<false>
{
template <class T>  struct non_specialized { enum { value =3D
false}; };
};

template <>  struct is_pointer_class_helper<true>
{
template <class T>  struct non_specialized { enum { value =3D
boost::is_pointer<T> ::value }; };
};

template <typename T> 
struct is_pointer
{
enum { temp_value =3D (sizeof(yes_type) =3D=3D=20
sizeof
(is_pointer_helper1(*is_pointer_helper2(type_wrapper<T> ())))) };
enum { value =3D
is_pointer_class_helper<temp_value> ::non_specialized<T>::value };
};

struct X; // incomplete class
struct Y { virtual void y() =3D 0; virtual ~Y() =3D 0 {}; }; // abstract
class
struct Z {}; // regular class
typedef Z W[3]; // array type
typedef Z& V; // reference

int main()
{
std::cout << is_pointer<W*> ::value << std::endl;
std::cout << is_pointer<X*> ::value << std::endl;
std::cout << is_pointer<Y*> ::value << std::endl;;
std::cout << is_pointer<Z*> ::value << std::endl;
std::cout << is_pointer<V> ::value << std::endl;
std::cout << is_pointer<W> ::value << std::endl;
std::cout << is_pointer<X> ::value << std::endl;
std::cout << is_pointer<Y> ::value << std::endl;;
std::cout << is_pointer<Z> ::value << std::endl;
return 0;
}

>  -----Original Message-----
>  From: David Abrahams [mailto: david.abrahams@[...].. ]
>  Sent: Wednesday, March 13, 2002 5:33 PM
>  To: boost@[...].com
>  Subject: [boost] type_traits: workaround bias
> =20
> =20
>  It seems that the known technologies for writing type traits for
>  compilers without partial specialization nearly always force us to
>  choose between supporting array types and supporting abstract classes.
>  Let's just look at is_pointer, for an example:
> =20
>  ----------
>  struct pointer_helper
>  {
>  pointer_helper(const volatile void*);
>  };
>  yes_type BOOST_TT_DECL is_pointer_helper(pointer_helper);
>  no_type BOOST_TT_DECL is_pointer_helper(...);
> =20
> =20
>  template <typename T>
>  struct is_pointer
>  {
>  private:
>  static T t;
>  public:
>  BOOST_STATIC_CONSTANT(bool, value =3D
>  (::boost::type_traits::ice_and<
>  ::boost::type_traits::ice_not<
>  ::boost::is_reference<T>::value
>  >::value,
>  ::boost::type_traits::ice_not<
>  ::boost::is_array<T>::value
>  >::value,
>  (::boost::type_traits::ice_or<
>  (1 =3D=3D sizeof(detail::is_pointer_helper(t))),
>  (1 =3D=3D sizeof(detail::is_function_tester(t)))
>  >::value)
>  >::value ) );
>  };
>  template <>
>  struct is_pointer <void>
>  {
>  BOOST_STATIC_CONSTANT(bool, value =3D false);
>  };
>  -----------
> =20
>  The above is our current implementation, which cannot be instantiated
>  when T is a class with an unimplemented pure virtual function.
> =20
>  Now let's examine an alternative implementation, which doesn't support
>  array types, but supports abstract classes:
> =20
>  ---------
>  template <class T>
>  yes_type BOOST_TT_DECL is_pointer_helper(T*(*)());
>  no_type BOOST_TT_DECL is_pointer_helper(...);
>  template <typename T>
>  struct is_pointer
>  {
>  public:
>  BOOST_STATIC_CONSTANT(bool, value =3D
>  (::boost::type_traits::ice_or<
>  (1 =3D=3D
>  sizeof(detail::is_pointer_helper((T(*)())0))),
>  (1 =3D=3D sizeof(detail::is_function_tester(t)))
>  >::value)
>  >::value ) );
>  };
>  ----------
> =20
>  Leaving aside from the technical argument that the 2nd version is much
>  simpler, I wonder if we have made the right choice in our support for
>  array types over abstract classes. In the work I'm doing,=20
>  with function
>  arguments and return values, it seems to me that abstract classes are
>  going to arise far more often than arrays.
> =20
>  In particular, it would be very useful to me if I could instantiate
>  is_class<T> for abstract classes. It's much less important to=20
>  me that it
>  work for array types.
> =20
>  Thoughts?
>  Dave
> =20
>  +---------------------------------------------------------------+
>  David Abrahams
>  C++ Booster ( http://www.boost.org ) O__ =3D=3D
>  Pythonista ( http://www.python.org ) c/ /'_ =3D=3D
>  resume: http://users.rcn.com/abrahams/resume.html (*) \(*) =3D=3D
>  email: david.abrahams@[...]..
>  +---------------------------------------------------------------+
> =20
> =20
>  Info: http://www.boost.org Send unsubscribe requests to:=20
>  <mailto: boost-unsubscribe@[...].com>=20
> =20
>  Your use of Yahoo! Groups is subject to=20
>  http://docs.yahoo.com/info/terms/=20
> =20
> =20

Privacy Policy | Email Opt-out | Feedback | Syndication
© ActiveState Software Inc. All rights reserved