I hope this won't be too vague but I don't want to be verbose. . . . I don't always seem to have this problem. I have this class, Text, whose objects consist of objects of another class, StringVar (they can be interpreted quite literally to infer what they are). Both have destructors. One of the member functions of Text is to copy a portion of the calling object and return a different Text object that represents the portion. Since Text's operator<< needs to do work, all I know to do is to declare a new Text object in this member function, adequately fill the object with StringVar objects and then return it. It works when there's no destructor for the class and doesn't work with the destructor. I don't remember having this problem with an analogous member function in StringVar when I was working on the textbook problem involving that class as the only user-defined class in the program (and in fact I was surprised at the time that the destructor apparently didn't have any effect on the returned object declared within the member function).
I'm guessing this would be a somewhat typical situation, so I spare you any code.
OK, you are copying objects, but you don't have a proper copy constructor.
Consider the following:
1 2 3 4 5 6 7 8 9 10 11 12 13
{
StringVar a("whatever"); // allocates memory for a.value
{
StringVar b = a; // copies a to b
// however!
// this doesn't actually copy the string data, it only copies the pointer
// now, b.value == a.value. They both point to the same data
} // here, b is destroyed
// this means that b's destructor will delete[] value.
// however note that 'a' is still using that buffer! This is bad
} // here, a is destroyed
// and it tries to delete[] value. But value was already deleted by b's destructor
// so your program explodes.
This is the source of your problem. You need to write copy constructors and assignment operators for these classes that actually "deep copy" the string data and not just copy the pointers.
Aha. I have a copy constructor and an assignment operator for the StringVar class but had neither for the Text class (even though the textbook problem suggested that I basically use all of the members of the StringVar class analogously for the Text class). That's why it worked for the StringVar class with the destructor, as I then took it too much for granted not really learning the lesson. Now I remember reading that the copy constructor and the =operator are part of "The Big Three" along with the destructor, where if one is needed all are needed.
So I know you're right even before I've written the code. I just needed you to hit me with it, with an added bonus that you gave me another good variant of the explanation. Thanks a lot, Disch.