$include_dir="/home/hyper-archives/boost/include"; include("$include_dir/msg-header.inc") ?>
From: Luis Pedro Coelho (deepblack9_at_[hidden])
Date: 2002-02-13 17:12:50
Em Quarta, 13 de Fevereiro de 2002 16:01, escreveste:
> When you do
>    A.value = 100 ;
> how does the property 'value' receives &A?
>
> My point is that there is NO WAY to store &A inside 'value' at compile
> time. You can store &A::foo, but without &A this still requires runtime
> support.
Off the top of my head:
value doesn't know where A is, but it knows where it is and it knows that it 
lies inside A. In typical implementations (the begginning of) A will lie in a 
fixed offset from where value is.
So
void value::operator = (const int x) {
        A* a = reinterpret_cast<A*>(reinterpret_cast<unsigned char*>(this) - offset);
        a->set_value(x);
}
All we got to do is find a way to calculate OFFSET at compile time. I think 
that something like:
T  A::*ptr = &A::value; 
A* A = reinterpret_cast<A*>(&ptr); 
        // <- I just use ptr, could be anything!
T* t = A->*ptr;
long offset = reinterpret_cast<unsigned char*>(t) - reinterpret_cast<unsigned 
char*>(A);
Of course, we can do this in one constant expression inside the template 
class definition:
        enum { offset = (reinterpret_cast<unsigned char*>
                (reinterpret_cast<unsigned char*>(&whatever)->*Ptr_to_member)
                 - 
                reinterpret_cast<unsigned char*>(&whatever)));
                }
Where Ptr_to_member is passed as a template parameter.
Note that we have to write:
        boost::property<A, &A::value, read<&A::get_x>, write<&A::set_x> > value;
This approach has at least one advantage: No need to store an extra pointer 
to the parent in every property object. Also there is now no need to pass to 
this as a constructor argument.
HTH,
-- Luis Pedro Coelho. Check out my game of Hearts, a card game, for KDE at: http://hearts.sourceforge.net/