Re: Stack overflow using boost::operators
 
On Dec 17, 3:32 pm, ManicQin <manic...@gmail.com> wrote:
Hello all,
while using boost::operators I bump into a stack overflow.
....
Using my debugger (visual studio 9 express) I jumped into
the operator.hpp and followed the sequence of the program,
for a reason I cannot understand in the first error line
which examples a T <= T operator I move from
less_than_comparable1::operator<=(const T& x, const T& y)
to
less_than_comparable2::operator<(const U& x, const T& y)
....
#include "boost/lexical_cast.hpp"
#include "boost/operators.hpp"
#include <iostream>
using namespace boost;
using namespace std;
....
template <class T>
class FieldOp : public T ,
  boost::ordered_field_operators<FieldOp<T>,
     boost::ordered_field_operators<FieldOp<T>,T,
                boost::ordered_field_operators<FieldOp<T>,typename T::FieldType
        > > >
{
public:
        FieldOp(typename T::FieldType const&  val) : T(val) {}
        FieldOp(T const&  val) : T(val.Data()) {}
        FieldOp(FieldOp<T> const&  val) : T(val.Data()) {}
        bool operator > (typename T::FieldType const& val)
        {
                return (Data() > val);
        }
        bool operator > (typename T const& val)
        {
                return (Data() > val.Data());
        }
        bool operator > (typename FieldOp<T> const& val)
        {
                return (Data() > val.Data());
        }
        bool operator < (typename T::FieldType const& val)
        {
                return Data() < val;
        }
        bool operator < (typename T const& val)
        {
                return Data() < val.Data();
        }
        bool operator < (typename FieldOp<T> const& val)
        {
                return Data() < val.Data();
        }
These functions should be const.
What's happening is that the boost defined
operator>(const FieldOp<IField<int>>&,const FieldOp<IField<int>>&)
takes your object by const reference, and then tries to call operator<
with the arguments swapped. Since your operator< isn't const it can't
be called on a const reference. Since const FieldOp<IField<int>>&
converts automatically to const IField<int>& due to a derived-to-base
conversion, you instead end up in the boost defined
operator<(const IField<int>&,const FieldOp<IField<int>>&)
which tries to call operator> with the arguments swapped. Since your
operator> isn't const it can't be called on a const reference. Since
IField<int> converts automatically to const FieldOp<IField<int>>& via
a converting constructor, you instead end up in the boost defined
operator>(const FieldOp<IField<int>>&,const FieldOp<IField<int>>&)
which is where we were before. And so on and so forth, until the stack
overflows.
Incidentally it's generally recommended to make your operators free
functions.
Yechezkel Mett
-- 
      [ See http://www.gotw.ca/resources/clcm.htm for info about ]
      [ comp.lang.c++.moderated.    First time posters: Do this! ]