Re: [boost] About member extraction

2003-07-14 Thread Joaquín Mª López Muñoz


John Torjo ha escrito:

> >
> >Subject: Re: [boost] About member extraction
> >   From: Joaquín Mª López Muñoz <[EMAIL PROTECTED]>
> >   Date: Mon, 14 Jul 2003 14:24:37 +0200
> > To: Boost mailing list <[EMAIL PROTECTED]>
> >
> >
> >
> >Daryle Walker ha escrito:
> >
> >> But doesn't the "PtrToMember" template parameter already imply the
> >> "Type" and "Class" parameters?  So specifying all three would be
> >> redundant.  Could we reduce it by:
> >>
> >> //
> >> template < typename PtrToMember >
> >> struct member_extractor
> >> {
> >>// Don't know if this is a real type-traits class
> >>BOOST_STATIC_ASSERT(is_pointer_data_member::value);
> >>
> >>// The extractor traits classes aren't real (yet, maybe)
> >>typedef get_class_type  argument_type;
> >>typedef get_member_type   return_type;
> >>
> >>return_type const &  operator ()( argument_type const &c ) const
> >>  { return c.*PtrToMember; }
> >>
> >>return_type &  operator ()( argument_type &c ) const
> >>  { return c.*PtrToMember; }
> >> };
> >
> >Of the approaches you propose, this is the one that I like best, but
> >I'm afraid it cannot be implemented: Note that PtrToMember is a
> >*type* (something like int A::*), not a pointer to member.
> >member_extractor would have to defined as
> >
> >template < typename PtrToMember, PtrToMember ptr >
> >struct member_extractor
> >
> >and used as
> >
> >member_extractor; // x is an int member of A
>
> Actually, I think it's worse (I don't have a C++ compiler with me right now:-( )
>
> Something in the lines of:
>
> template < typename type, typename result, result type::* ptr >
> struct member_extractor
>
>

Actually, extracting "A" and "int" from "int A::*" is easy:

#include 
#include 

using namespace std;

struct A
{
  int x;
};

template 
struct ptr_to_member_descriptor;

template 
struct ptr_to_member_descriptor
{
  typedef Class  class_type;
  typedef Member member_type;
};

int main()
{
  BOOST_STATIC_ASSERT((
boost::is_same<
  ptr_to_member_descriptor::class_type,
  A>::value));

  BOOST_STATIC_ASSERT((
boost::is_same<
  ptr_to_member_descriptor::member_type,
  int>::value));

  return 0;
}


The really hard part is how to obtain "int A::*" from "&A::x". I don't
think this is possible, but then again people here sometimes do magic :)

Joaquín M López Muñoz
Telefónica, Investigación y Desarrollo

___
Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost


Re: [boost] About member extraction

2003-07-14 Thread John Torjo
>
>Subject: Re: [boost] About member extraction
>   From: Joaquín Mª López Muñoz <[EMAIL PROTECTED]>
>   Date: Mon, 14 Jul 2003 14:24:37 +0200
> To: Boost mailing list <[EMAIL PROTECTED]>
>
>
>
>Daryle Walker ha escrito:
>
>> But doesn't the "PtrToMember" template parameter already imply the
>> "Type" and "Class" parameters?  So specifying all three would be
>> redundant.  Could we reduce it by:
>>
>> //
>> template < typename PtrToMember >
>> struct member_extractor
>> {
>>// Don't know if this is a real type-traits class
>>BOOST_STATIC_ASSERT(is_pointer_data_member::value);
>>
>>// The extractor traits classes aren't real (yet, maybe)
>>typedef get_class_type  argument_type;
>>typedef get_member_type   return_type;
>>
>>return_type const &  operator ()( argument_type const &c ) const
>>  { return c.*PtrToMember; }
>>
>>return_type &  operator ()( argument_type &c ) const
>>  { return c.*PtrToMember; }
>> };
>
>Of the approaches you propose, this is the one that I like best, but
>I'm afraid it cannot be implemented: Note that PtrToMember is a
>*type* (something like int A::*), not a pointer to member.
>member_extractor would have to defined as
>
>template < typename PtrToMember, PtrToMember ptr >
>struct member_extractor
>
>and used as
>
>member_extractor; // x is an int member of A

Actually, I think it's worse (I don't have a C++ compiler with me right now:-( )

Something in the lines of:

template < typename type, typename result, result type::* ptr >
struct member_extractor


>
>which takes us again to the redundancy we were trying to avoid.
>Something in the way of eliminating this redundancy, however, would be
>a boon. Maybe some metaprogramming gurus here can think of
>something.
>

I would really love to see a solution to this ;-)

Best,
John


>Joaquín M López Muñoz
>Telefónica, Investigación y Desarrollo
>
>___
>Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost

___
Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost


Re: [boost] About member extraction

2003-07-14 Thread Joaquín Mª López Muñoz


Daryle Walker ha escrito:

> But doesn't the "PtrToMember" template parameter already imply the
> "Type" and "Class" parameters?  So specifying all three would be
> redundant.  Could we reduce it by:
>
> //
> template < typename PtrToMember >
> struct member_extractor
> {
>// Don't know if this is a real type-traits class
>BOOST_STATIC_ASSERT(is_pointer_data_member::value);
>
>// The extractor traits classes aren't real (yet, maybe)
>typedef get_class_type  argument_type;
>typedef get_member_type   return_type;
>
>return_type const &  operator ()( argument_type const &c ) const
>  { return c.*PtrToMember; }
>
>return_type &  operator ()( argument_type &c ) const
>  { return c.*PtrToMember; }
> };

Of the approaches you propose, this is the one that I like best, but
I'm afraid it cannot be implemented: Note that PtrToMember is a
*type* (something like int A::*), not a pointer to member.
member_extractor would have to defined as

template < typename PtrToMember, PtrToMember ptr >
struct member_extractor

and used as

member_extractor; // x is an int member of A

which takes us again to the redundancy we were trying to avoid.
Something in the way of eliminating this redundancy, however, would be
a boon. Maybe some metaprogramming gurus here can think of
something.

Joaquín M López Muñoz
Telefónica, Investigación y Desarrollo

___
Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost


[boost] About member extraction

2003-07-12 Thread Daryle Walker
In another thread, by Joaquín M López Muñoz, there is talk of a helper 
class like:

//
template<
  class Class,typename Type,
  Type Class::*PtrToMember,
  typename Compare=std::less >
struct less_by
{
  less_by(const Compare& comp=Compare()):comp(comp){}
  bool operator()(const Class& x,const Class& y)const
  {
return comp(x.*PtrToMember,y.*PtrToMember);
  }
  bool operator()(const Type& x,const Class& y)const
  {
return comp(x,y.*PtrToMember);
  }
  bool operator()(const Class& x,const Type& y)const
  {
return comp(x.*PtrToMember,y);
  }
private:
  Compare comp;
};
//
[That was cut from the "multindex" trial code.]  The author later 
decided to segregate the extraction from the comparison.  No code has 
been given yet, but that class could be like:

//
template<
  class Class,typename Type,
  Type Class::*PtrToMember >
struct member
{
Type const &  operator ()( Class const &c ) const
{ return c.*PtrToMember; }
Type &  operator ()( Class &c ) const
{ return c.*PtrToMember; }
};
//
But doesn't the "PtrToMember" template parameter already imply the 
"Type" and "Class" parameters?  So specifying all three would be 
redundant.  Could we reduce it by:

//
template < typename PtrToMember >
struct member_extractor
{
  // Don't know if this is a real type-traits class
  BOOST_STATIC_ASSERT(is_pointer_data_member::value);
  // The extractor traits classes aren't real (yet, maybe)
  typedef get_class_type  argument_type;
  typedef get_member_type   return_type;
  return_type const &  operator ()( argument_type const &c ) const
{ return c.*PtrToMember; }
  return_type &  operator ()( argument_type &c ) const
{ return c.*PtrToMember; }
};
//
Or we can simplify the type extraction, at the cost/gain of needing to 
specify the exact member at construction time by:

//
template < class Class, typename Type >
class member_extractor
{
public:
  typedef Class  argument_type;
  typedef Type return_type;
  typedef Type Class::*  member_type;

  explicit member_extractor( member_type m )
: member_( m ) {}
  return_type const &  operator ()( argument_type const &c ) const
{ return c.*member_; }
  return_type &  operator ()( argument_type &c ) const
{ return c.*member_; }
  member_type get_member() const
{ return this->member_; }
private:
  member_type  member_;
};
//
Daryle

___
Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost