By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
454,925 Members | 1,164 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 454,925 IT Pros & Developers. It's quick & easy.

Operator overloading: s1 = s1 + s1;

P: n/a
Hi.

I am just sharpening up some code, getting operators going,
but have bumped into a hurdle around applying operators to the
following line of code:

s1 = s1 + s1;

where s1 is a class containing a pointer array of doubles.
I'm finding it difficult to plug a memory leak.
Has anyone been here before?
Any help will be appreciated.
The sum operation isn't the real problem; the product is.
The product requires prezeroing its destination(return value).
Even if you can only explain why I shouldn't attempt this in my own
home I will be gratefull.

It may be that my most practical solution is to abandon the use of
class references and go straight to pointers.
The product requires allocation. I've tried with and without an =
operator.
The copy constructor does take over the assignment, or at least the
code compiles. Oops, that might be it. My copy constructor is not doing
it, but an automatic one is. Well, I'll check this out but I doubt that
it is the problem.

Gee, thanks a lot for being here.

-Tim

Aug 5 '05 #1
Share this Question
Share on Google+
6 Replies


P: n/a
tt*******@yahoo.com wrote:
I am just sharpening up some code, getting operators going,
but have bumped into a hurdle around applying operators to the
following line of code:

s1 = s1 + s1;

where s1 is a class containing a pointer array of doubles.
OK. Have you tried a 'vector<double>' instead of the array?
I'm finding it difficult to plug a memory leak.
Has anyone been here before?
What memory leak?
Any help will be appreciated.
The sum operation isn't the real problem; the product is.
I.e.

s1 = s1 * s1;

?
The product requires prezeroing its destination(return value).
Even if you can only explain why I shouldn't attempt this in my own
home I will be gratefull.
Hey, it's your home, do as you please, we're not going to tell you
otherwise. Now, without seeing what your operator+ or operator*
looks like, or how the class is defined, there is no advice to give.
It may be that my most practical solution is to abandon the use of
class references and go straight to pointers.
Huh?
The product requires allocation. I've tried with and without an =
operator.
Huh? You should consider explaining what you mean by that.
The copy constructor does take over the assignment
How does that happen?
, or at least the
code compiles. Oops, that might be it. My copy constructor is not
doing it, but an automatic one is. Well, I'll check this out but I
doubt that it is the problem.


V
Aug 5 '05 #2

P: n/a
tt*******@yahoo.com wrote:
Hi.

I am just sharpening up some code, getting operators going,
but have bumped into a hurdle around applying operators to the
following line of code:

s1 = s1 + s1;

where s1 is a class containing a pointer array of doubles.
Operators cannot be used on classes. Did you mean "... s1 is an instance of
a class ..."?
I'm finding it difficult to plug a memory leak.
Has anyone been here before?
Probably.
Any help will be appreciated.
How should we help you find a problem in code we don't see? Not everyone
here is able to find out your IP, hack in to your computer and read your
source code from it. ;-)
The sum operation isn't the real problem; the product is.
What product?
The product requires prezeroing its destination(return value).
?
Even if you can only explain why I shouldn't attempt this in my own
home I will be gratefull.
I don't care what you attempt in your home. However, it's unlikely that you
blow yourself up trying "this", whatever you actually mean.
It may be that my most practical solution is to abandon the use of
class references and go straight to pointers.
Huh? What does that have to do with your problem?
The product requires allocation. I've tried with and without an =
operator.
The copy constructor does take over the assignment, or at least the
code compiles.
The copy constructor never "takes over" an assignment. However, if you don't
define your own operator=, the compiler automatically generates one for you
that does a memberwise copy. If your class allocates resources (like
memory), this is probably not what you want. This is the Rule of Three:
If you need your own copy constructor, assignment operator or destructor,
you probably need all three of them.
Oops, that might be it. My copy constructor is not doing
it, but an automatic one is.


Doing what?

Aug 5 '05 #3

P: n/a
I believe that there is a misnomer in C++'s algebraic operators being
overloadable.
I am open to being wrong of course since I would like to get my code to
work.
The nSigned class has algebraic sum and product functions that work
fine until something like s1.Product( s1, s1) happens. I am trying to
resolve this conflict via operators but am merely bumping into the same
conflict in a more complicated form.

I've reinstituted the assignment (=) operator. I was mistaken about the
copy constructor substituting in lieu of it. So now I have a memory
leak. As I see it this memory leak is due to the need to create a new
nSigned instance to hold the sum or product operation resultant. But
upon completion of the assignment deletion of the old value is not
necessarily appropriate. For example, s1 = s2 + s3 should work as well
as s1 = s1 + s1, but coding s1 = s2 should also be valid.

Here is the pertinent code:

class nSigned
{
public:
int n; // the number of signs
double * x; // the vector
int error; // error field
nSigned( const int n );
nSigned( const nSigned & s );
nSigned();
~nSigned();
int nSigned::operator = (const nSigned & s );
//nSigned & operator @ (const nSigned & s1, const nSigned & s2 );
double Reduce();
int Zero();
int Sum( const nSigned & n1, const nSigned & n2 );
nSigned operator + ( const nSigned & s1 ); // sum operator
int Product( const nSigned & n1, const nSigned & n2 );
nSigned operator * ( const nSigned & s1 ); // product operator
int Print( );
};

nSigned::nSigned( const nSigned & s )
{
n = s.n;
x = new double[n];
int i;
for( i = 0; i < n; i++ )
{
x[i] = s.x[i];
}
error = s.error;
}
nSigned::nSigned( const int numsigns )
{
n = numsigns;
x = new double[numsigns];
int i;
for( i = 0; i < n; i++ )
{
x[i] = 0;
}
error = 0;
}
nSigned::~nSigned()
{
delete[] x;
n = 0;
}
int nSigned::operator = (const nSigned & s )
{
if( n != s.n )
{
error |= ERROR_DimensionMismatch;
return -1;
}
int i;
for( i = 0; i < n; i++ )
{
x[i] = s.x[i];
}
error = s.error;
return error;
}

int nSigned::Sum( const nSigned & s1, const nSigned & s2 )
{
int i;
if( s1.n != n || s2.n != n )
{ // for now require dimensional match
error |= ERROR_Sum | ERROR_DimensionMismatch;
return -1;
}
for( i = 0; i < n; i++ )
{
x[i] = s1.x[i] + s2.x[i];
}
Reduce();
return 0;
}
nSigned nSigned::operator + ( const nSigned & s1 )
{ // sum operator
nSigned * sp = new nSigned(n);
sp->Sum( s1, *this );
return * sp;
}

int nSigned::Product( const nSigned & s1, const nSigned & s2)
{
int i;
int j;
int k;
if( s1.n != n || s2.n != n )
{ // for now require dimensional match
error |= ERROR_Product | ERROR_DimensionMismatch;
return -1;
}
if( x == s1.x || x == s2.x )
{ // s1.Product(s1,s2) is illegal since s1.x[] gets wiped clean
error |= ERROR_Product;
return -1;
}

Zero();
for( i = 0; i < n; i++ )
{
for( j = 0; j < n; j++ )
{
k = (i+j)%n;
x[ k ] += s1.x[i] * s2.x[j];
}
}
Reduce();
return 0;
}
nSigned nSigned::operator * ( const nSigned & s1 )
{ // product operator
nSigned * sp = new nSigned( n );
sp->Product( s1, *this );
return *sp;
}

Aug 9 '05 #4

P: n/a
tt*******@yahoo.com wrote:
I believe that there is a misnomer in C++'s algebraic operators being
overloadable.
Huh?
I am open to being wrong of course since I would like to get my code to
work.
"Open to being wrong"? As in "I welcome being wrong"?
The nSigned class has algebraic sum and product functions that work
fine until something like s1.Product( s1, s1) happens.
What is it supposed to do?
I am trying to
resolve this conflict via operators but am merely bumping into the same
conflict in a more complicated form.

I've reinstituted the assignment (=) operator. I was mistaken about the
copy constructor substituting in lieu of it. So now I have a memory
leak.
Of course you do. Why do you need 'new' there _at_all_?
As I see it this memory leak is due to the need to create a new
nSigned instance to hold the sum or product operation resultant. But
upon completion of the assignment deletion of the old value is not
necessarily appropriate. For example, s1 = s2 + s3 should work as well
as s1 = s1 + s1, but coding s1 = s2 should also be valid.

Here is the pertinent code:

class nSigned
{
public:
int n; // the number of signs
double * x; // the vector
int error; // error field
Why are the data members public?
nSigned( const int n );
nSigned( const nSigned & s );
nSigned();
~nSigned();
int nSigned::operator = (const nSigned & s );
//nSigned & operator @ (const nSigned & s1, const nSigned & s2 );
double Reduce();
int Zero();
int Sum( const nSigned & n1, const nSigned & n2 );
What's it do? Make 'this' object the sum of its arguments?
nSigned operator + ( const nSigned & s1 ); // sum operator
int Product( const nSigned & n1, const nSigned & n2 );
What's it do? Make 'this' object the product of its arguments?
nSigned operator * ( const nSigned & s1 ); // product operator
int Print( );
};

nSigned::nSigned( const nSigned & s )
{
n = s.n;
x = new double[n];
What if 'n' is 0?
int i;
for( i = 0; i < n; i++ )
{
x[i] = s.x[i];
}
error = s.error;
}
nSigned::nSigned( const int numsigns )
No error checking for 'numsigns' being <= 0. BTW, top-level 'const'
is meaningless, really.
{
n = numsigns;
x = new double[numsigns];
int i;
for( i = 0; i < n; i++ )
{
x[i] = 0;
}
error = 0;
}
nSigned::~nSigned()
{
delete[] x;
n = 0;
}
int nSigned::operator = (const nSigned & s )
Why does your copy assignment operator return 'int'? That's unusual,
you know...
{
if( n != s.n )
{
error |= ERROR_DimensionMismatch;
return -1;
}
int i;
for( i = 0; i < n; i++ )
{
x[i] = s.x[i];
}
error = s.error;
return error;
}

int nSigned::Sum( const nSigned & s1, const nSigned & s2 )
{
int i;
if( s1.n != n || s2.n != n )
{ // for now require dimensional match
error |= ERROR_Sum | ERROR_DimensionMismatch;
return -1;
}
for( i = 0; i < n; i++ )
{
x[i] = s1.x[i] + s2.x[i];
}
Reduce();
What does 'Reduce' do?
return 0;
}
nSigned nSigned::operator + ( const nSigned & s1 )
{ // sum operator
nSigned * sp = new nSigned(n);
Why? Couldn't you just say

nSigned sp(n);
sp->Sum( s1, *this );
and
sp.Sum(*this, s1);
return * sp;
and
return sp;

???
}

int nSigned::Product( const nSigned & s1, const nSigned & s2)
Can you explain what you expect this function to do?
{
int i;
int j;
int k;
Why are you declaring those variables _WAAAAY_ before they are used?
Are you a C programmer?
if( s1.n != n || s2.n != n )
{ // for now require dimensional match
error |= ERROR_Product | ERROR_DimensionMismatch;
return -1;
}
if( x == s1.x || x == s2.x )
{ // s1.Product(s1,s2) is illegal since s1.x[] gets wiped clean
error |= ERROR_Product;
return -1;
}

Zero();
Does that do what I think it does? Why do you think you need this?
for( i = 0; i < n; i++ )
{
for( j = 0; j < n; j++ )
{
k = (i+j)%n;
x[ k ] += s1.x[i] * s2.x[j];
}
}
Reduce();
return 0;
}
nSigned nSigned::operator * ( const nSigned & s1 )
{ // product operator
nSigned * sp = new nSigned( n );
sp->Product( s1, *this );
return *sp;
}


I cannot compile your code (whether it's "pertinent" or not). Next
time post _complete_ code.
V
Aug 9 '05 #5

P: n/a
tt*******@yahoo.com wrote:
nSigned nSigned::operator + ( const nSigned & s1 )
{ // sum operator
nSigned * sp = new nSigned(n);
sp->Sum( s1, *this );
return * sp;
}
That's a memory leak. Who will delete the object you created?

nSigned nSigned::operator+(const nSigned &s)
{
nsigned sp(n);
sp.Sum(s, *this);
return sp;
}
nSigned nSigned::operator * ( const nSigned & s1 )
{ // product operator
nSigned * sp = new nSigned( n );
sp->Product( s1, *this );
return *sp;
}


Same here.

What book are you reading?
Jonathan

Aug 9 '05 #6

P: n/a
Thanks guys.

The code has gone through some iterations and you are finding new bugs
as a result of experimenting with ways to fix old ones.

I just turned up solid example code of an assignment operation in
Strousstrup under "Copying Objects" that I hadn't seen before in
operator overloading. So yes the operators + and * should not use new,
but instead pass it on the stack and the = operator does delete the
temporary instance that is on the stack. Now the memory leak is gone
and the results look accurate.

Thanks also for the other morsels.

-Tim
Victor, you ask about the product operation. It is a polysigned
product.
It turns out that for example when n is 3 this product is equivalent to
that of the complex numbers. Beyond three things get weird but are
still of interest.

Sorry, I didn't realize you would try to compile the code. I left out
the Reduce function didn't I. If you are really curious about what the
code does please go to :
http://bandtechnology.com/PolySigned/PolySigned.html
The nSigned class is polysigned numbers. There is quite a bit more code
that I've snipped out of the above sample.

Aug 9 '05 #7

This discussion thread is closed

Replies have been disabled for this discussion.