Nicolay Korslund wrote:
Hi! I'm having a little trouble with the typecast operator, can anybody
help me with the rules for when the this operator is invoked?
In the class 'Test' in the code below, the typecast operator returns a
'mytype'. In main() I use the [] operator on 'Test'-class objects. If
'mytype' is a pointer the [] operator works fine. But if I instead try
to call an overloaded [] operator, the typecast operator is not invoked,
and I get a compiler error (unless I make an explicit cast.) So does the
'operator mytype ()' only work properly with simple types?
Any help would be appreciated!
Nico
template <class mytype>
class Test
{
mytype i;
public:
operator mytype () {return i;}
};
class Test2
{
public:
int operator [] (int i) {return i;}
};
int main(void)
{
Test<double*> t1;
Test<Test2> t2;
t1[0]; // This line works fine
t2[0]; // This line doesn't compile
((Test2)t2)[0]; // This also works
return 0;
}
I'm not sure why the code above does not work. There seems to be only
one conversion operator and one operator[] definition. I looked through
the copy of the standard I have and it is unfortunatly very wordy about
the subject and hard to filter the relevant pieces.
This is another version of your example that does work. (at least on gcc
3.3.1).
template <class mytype> class TestProxy;
template <class mytype>
class Test
{
friend class TestProxy<mytype>;
mytype v;
public:
operator mytype & ()
{
return v;
}
TestProxy<mytype> operator [] (int i);
};
template <typename T>
class PtrType
{
public:
typedef int Type; // HACK ALERT
};
template <typename T>
class PtrType<T*>
{
public:
typedef T & Type;
};
template <class mytype> class TestProxy
{
public:
Test<mytype> & m_test;
int m_i;
TestProxy( Test<mytype> & i_test, int i )
: m_test( i_test ),
m_i( i )
{
}
operator typename PtrType<mytype>::Type ()
{
return m_test.v[m_i];
}
};
template <class mytype>
inline TestProxy<mytype> Test<mytype>::operator [] (int i)
{
return TestProxy<mytype>( *this, i );
}
class Test2
{
public:
int operator [] (int i)
{
return i;
}
};
int main(void)
{
Test<double*> t1;
Test<Test2> t2;
t1[1]; // This line works fine
int x = t2[2]; // This line doesn't compile
((Test2)t2)[3]; // This also works
return 0;
}