Connecting Tech Pros Worldwide Forums | Help | Site Map

reinterpret_cast<> and UB

Nate Barney
Guest
 
Posts: n/a
#1: Sep 7 '06
I have:

// base class for Vector and Matrix
template <unsigned N,typename Value=float>
class NonScalar
{
public:

Value *ptr() { return e; }
const Value *ptr() const { return e; }

private:

Value e[N];
};

// Vector class
template <unsigned N,typename Value=float>
class Vector : public NonScalar<N,Value>
{
public:

Vector() {}
Vector(const NonScalar<N,Value&ns) : NonScalar<N,Value>(ns) {}
};

// Matrix class
template <unsigned R,unsigned C,typename Value=float>
class Matrix : public NonScalar<R * C,Value>
{
public:

Matrix() {}
Matrix(const NonScalar<R * C,Value&ns) : NonScalar<R *
C,Value>(ns) {}

// Matrix multiplication operator
template <unsigned N>
Matrix<R,N,Valueoperator*(const Matrix<C,N,Value&m) const;
}

// Matrix * Vector operator
template <unsigned R,unsigned C,typename Value>
inline Vector<R,Valueoperator*(const Matrix<R,C,Value&m,
const Vector<C,Value&v)
{
return static_cast<const Vector<R,Value>&>(m *
static_cast<const Matrix<C,1,Value>&>(v));
}

// Vector * Matrix operator
template <unsigned R,unsigned C,typename Value>
inline Vector<C,Valueoperator*(const Vector<R,Value&v,
const Matrix<R,C,Value&m)
{
return static_cast<const Vector<C,Value>&>(
static_cast<const Matrix<1,R,Value>&>(v) * m);
}

The v*m and m*v operators work correctly, but the second static_cast<>
in each one copies the contents of the Vector into a temporary Matrix,
via the NonScalar copy constructor. What I'd like to do is replace
this cast with a reinterpret_cast<>, which would simply treat the
Vector like a Matrix for the purposes of the call. The question is:
would doing so invoke undefined behavior? If so, is there a way to
make these operators work without copying their contents?

Thanks,
Nate


Nate Barney
Guest
 
Posts: n/a
#2: Sep 7 '06

re: reinterpret_cast<> and UB


Nate Barney wrote:
Quote:
>
// Matrix class
template <unsigned R,unsigned C,typename Value=float>
class Matrix : public NonScalar<R * C,Value>
{
/* snip */
}
Oops, forgot the semicolon here.

Ron Natalie
Guest
 
Posts: n/a
#3: Sep 8 '06

re: reinterpret_cast<> and UB


Nate Barney wrote:
Quote:
>
The v*m and m*v operators work correctly, but the second static_cast<>
in each one copies the contents of the Vector into a temporary Matrix,
via the NonScalar copy constructor. What I'd like to do is replace
this cast with a reinterpret_cast<>, which would simply treat the
Vector like a Matrix for the purposes of the call. The question is:
would doing so invoke undefined behavior? If so, is there a way to
make these operators work without copying their contents?
>
No. The fact that the two classes are derived from a common base
and there are no virtual functions in play or data members in the
derived class indicate it might work, the standard doesn't require
it.

What I might do to accomplish this is provide a Matrix class
(or a Matrix-like) class that is initialized with a Vector
and gets at the underlying NonScalar by reference rather than
making a copy.
Nate Barney
Guest
 
Posts: n/a
#4: Sep 8 '06

re: reinterpret_cast<> and UB


Ron Natalie wrote:
Quote:
>
No. The fact that the two classes are derived from a common base
and there are no virtual functions in play or data members in the
derived class indicate it might work, the standard doesn't require
it.
That's what I was afraid of. Oh well. Thanks for clearing that up for
me.
Quote:
What I might do to accomplish this is provide a Matrix class
(or a Matrix-like) class that is initialized with a Vector
and gets at the underlying NonScalar by reference rather than
making a copy.
That's not a bad idea. I'm also thinking about pushing operator*
down to NonScalar. I'll have to do a bit more thinking, though,
it seems.

Thanks again,
Nate

Closed Thread