Discussion:
destructors behaving weird
(too old to reply)
Yi Chai
2003-11-30 00:41:48 UTC
Permalink
I have decided to do more testing when I was really bored this afternoon,
and something really strange happened with my destructor.

I put in tester.body the following

q.Enqueue('a');
q.Enqueue('b');
q2.Enqueue('c');
q2.Enqueue('d');
q2.Enqueue('e');

q2 = q;
*q3 = q2;

delete &q;
delete q3;
delete &q2; <<<<<<<<<

now, if I comment out the line pointed to by <<<<<<, then the program works
fine.
I have put in some cout functions that prints hello in my destructors to
test it.
If I comment out that last line, hello is output 3 times, which is correct,
because i manually deleted q and q3 and also when program ends, memory
deleted q2.

but if I have that last line in there, trying to manually delete q2, a
segmentation fault occurs right after 3 lines of hello are output.

anyone see anything potentially wrong with this? My program worked fine
before this.
Michael Ens
2003-11-30 06:03:09 UTC
Permalink
Post by Yi Chai
delete &q;
delete q3;
delete &q2; <<<<<<<<<
If you ever use delete, it's a good bet you're doing something wrong if you
also use the & operator -- you should only delete memory allocated by
pointers. Nevertheless, here's what's happening:

We have:
q, q3 -> q2

You delete &q, now there is

GARBAGE, q3 -> q2

You delete q3, now you have

GARBAGE, q3 -> GARBAGE

Where did q2 go? You just deleted it: q3 points to q2, and delete deletes
whatever is pointed to. Now the line

delete &q2

is going to cause problems, because you are trying to delete memory that is
not yours: the garbage belongs to the operating system.

So, why, then, does it print "hello" three times? While I don't have a
definitive answer, I suspect it is just a weird side effect of your illegal
deleting (you broke the function contract, check you outlook address book!).
When you delete *q3, the destructor is called, but q2 finds itself being
deleted, and also calls its destructor. Perhaps that would become more
clear to you if you put your cout statement in the part of your destructor
that loops (I assume you have one...) and then counting how many hello's you
get. My guess is 5, and I hope you can see why, but I don't want to give
away stuff (messageboard rules and all).
Post by Yi Chai
I have decided to do more testing when I was really bored this afternoon,
and something really strange happened with my destructor.
I put in tester.body the following
q.Enqueue('a');
q.Enqueue('b');
q2.Enqueue('c');
q2.Enqueue('d');
q2.Enqueue('e');
q2 = q;
*q3 = q2;
delete &q;
delete q3;
delete &q2; <<<<<<<<<
now, if I comment out the line pointed to by <<<<<<, then the program works
fine.
I have put in some cout functions that prints hello in my destructors to
test it.
If I comment out that last line, hello is output 3 times, which is correct,
because i manually deleted q and q3 and also when program ends, memory
deleted q2.
but if I have that last line in there, trying to manually delete q2, a
segmentation fault occurs right after 3 lines of hello are output.
anyone see anything potentially wrong with this? My program worked fine
before this.
Yi Chai
2003-11-30 16:53:22 UTC
Permalink
sorry, I left out some information
i declared q and q2 as normal Queue, but q3 as a Queue*, and the following
line was there too
q3 = new Queue;

so shouldn't *q3 = q2 make a deep copy of q2?

also I modified the tester.body and got rid of q3. So now I have

delete &q;
delete &q2;

It get through first one perfectly, but give segmentation fault right after
second line.

maybe the code itself is wrong because we can not delete them like that.
Post by Michael Ens
Post by Yi Chai
delete &q;
delete q3;
delete &q2; <<<<<<<<<
If you ever use delete, it's a good bet you're doing something wrong if you
also use the & operator -- you should only delete memory allocated by
q, q3 -> q2
You delete &q, now there is
GARBAGE, q3 -> q2
You delete q3, now you have
GARBAGE, q3 -> GARBAGE
Where did q2 go? You just deleted it: q3 points to q2, and delete deletes
whatever is pointed to. Now the line
delete &q2
is going to cause problems, because you are trying to delete memory that is
not yours: the garbage belongs to the operating system.
So, why, then, does it print "hello" three times? While I don't have a
definitive answer, I suspect it is just a weird side effect of your illegal
deleting (you broke the function contract, check you outlook address book!).
When you delete *q3, the destructor is called, but q2 finds itself being
deleted, and also calls its destructor. Perhaps that would become more
clear to you if you put your cout statement in the part of your destructor
that loops (I assume you have one...) and then counting how many hello's you
get. My guess is 5, and I hope you can see why, but I don't want to give
away stuff (messageboard rules and all).
Post by Yi Chai
I have decided to do more testing when I was really bored this afternoon,
and something really strange happened with my destructor.
I put in tester.body the following
q.Enqueue('a');
q.Enqueue('b');
q2.Enqueue('c');
q2.Enqueue('d');
q2.Enqueue('e');
q2 = q;
*q3 = q2;
delete &q;
delete q3;
delete &q2; <<<<<<<<<
now, if I comment out the line pointed to by <<<<<<, then the program
works
Post by Yi Chai
fine.
I have put in some cout functions that prints hello in my destructors to
test it.
If I comment out that last line, hello is output 3 times, which is
correct,
Post by Yi Chai
because i manually deleted q and q3 and also when program ends, memory
deleted q2.
but if I have that last line in there, trying to manually delete q2, a
segmentation fault occurs right after 3 lines of hello are output.
anyone see anything potentially wrong with this? My program worked fine
before this.
Loading...