Re: Keeping type safety for classes derived from template class adapters and few good practice questions
Shimon Shvartsbroit <shimon1981@gmail.com> wrote:
Hello all,
template <int N, typename T>
class VectorAdapter:public boost::additive<VectorAdapter<N, T> >
{
public:
typedef VectorAdapter<N, T> ValueType;
// implementation for operators manipulation
ValueType& operator+=(const ValueType& rhs)
{
for (size_t i = 0; i < N; ++i)
{
elements_[i] += rhs.elemens_[i];
}
return *this;
}
protected:
T elements_[N];
};
By using Boost.Operators I have a non member function defined for
operator + as follows:
template <int N, typename T>
VectorAdapter<N, T> operator+(const VectorAdapter<N, T>& lhs,
const VectorAdapter<N, T>& rhs);
One possible solution would be to declare VectorAdapter as:
template <int N, typename T, int ClassIdNumber>
ClassIdNumber - unique number for each class derived from
VectorAdapter.
class Vector4: public VectorAdapter<4, float, 0> {..};
class Color4: public VectorAdapter<4, float, 1> {..};
class Other4: public VectorAdapter<4, float, 2> {..};
I am sure there's a better approach.
There is, it is commonly refered to ax CRTP and it involves creating
a base class templated on the The derived class as well as what ever
other template args required. You used it with boost::additive. Note
boot::additives template paramenter is the name of its derived class.
Now on to the 'fixing' of vector_adaptor...
template <class Derived,class T,int N>
class vector_adaptor:boost::additive<vector_adaptor<Derived,T,N> >
{
protected:
T elements[N];
public:
Derived & operator += (const Derived &x)
{
for(int i=0;i!=N;++i)
elements[i] += x.elements[i];
return static_cast<Derived &>(*this);
}
Derived & operator -= (const Derived &x)
{
for(int i=0;i!=N;++i)
elements[i] -= x.elements[i];
return static_cast<Derived &>(*this);
}
T & operator [](int x) {return elements[i];}
const T & operator [](int x) const {return elements[i];}
};
class Vector4:public vector_adaptor<Vector4,float,4>{};
class Color4:public vector_adaptor<Color4,float,4>{};
now the classes passed to boost::aditive<...> are different and operator
+ wilth different 4 element vectors will not compile.
Not tested with boost, but It appears to solve the problem without
adding any complexity to the hierarchies involved beyond the
vector_adaptor class. It does compile with a simple operators lookalike
on this old compiler...
[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]