3

I realise this question has come up a few times, but I'm trying to get a definitive answer for the above question, but I keep coming across conflicting info. What I need to know is if a basic class object is destructed when I use exit(). I'm aware of dynamic memory needing to be deleted, but I am meaning something more like:

#include <iostream>
#include <string>
#include <stdlib.h>
using namespace std;

class employee
{
    public:
        employee ();
        string name;
        ~employee();
};

employee::employee () 
{
    name = "bob";
}

employee::~employee()
{
    cout << "Object destroyed" << endl;
}

int main()
{
    employee emp1;
    exit(1);
    cout << "Hello" << endl;
}

Now if I remove exit(1) from the main, the "Object destroyed" and "Hello" are printed as expected. Leaving it in there though, neither are printed. The reason is obvious for "Hello", but I was under the impression that emp1 would still be destructed, but the destruct message isn't shown...

I was looking at this link and it says about static objects being destroyed. Is the above object not considered static?

If not, is there a way to have a program terminate without it screwing with memory? My project revolves around user input and I was trying to give the option to exit if the user inputs the word 'exit'.

if(input_var == "exit")
    {
        cout << "You have chosen to exit the program." << endl;
        exit(1);
    }

Is a rough example of what my intent was.

Dwayne H
  • 235
  • 2
  • 11

4 Answers4

2

According to this link, it does not clean up the object. Note that if you use non-stack memory, it will call the destructor:

static employee emp1;

Second note. Any time you are using cout for debugging edge cases, timing critical debugging, etc., you should add a cout.flush() right after the coutto ensure your output is printed before it moves on. I have seen many people use cout for debugging crashes and the output never prints because the program terminates before the OS had a chance to print the output.

jaybers
  • 1,991
  • 13
  • 18
  • So would it be feasible to have my objects created by the user be created statically, so that exit destructs them? Once the object is made, the only thing that can be done with it is removal, so no values are available for changing. – Dwayne H Oct 24 '15 at 03:30
  • 1
    Yes that is one option. You will notice that if you put static in front of the declaration, the constructor is called even if exit() is called. – jaybers Oct 24 '15 at 03:37
1

Your emp1 variable is allocated on the stack. exit does not destroy local stack based variables.

1201ProgramAlarm
  • 32,384
  • 7
  • 42
  • 56
  • So is there a way to make the exit option back out of the entire program safely? I can make an exit function that destructs the dynamic objects, as there are a set number of those created, but that still wont work for my non-dynamic objects as the number of them depends on how many the user makes. – Dwayne H Oct 24 '15 at 03:22
  • 1
    Either return back up the call chain to main, or throw an exception that is caught in main. Exception handling will clean up all those locals. – 1201ProgramAlarm Oct 24 '15 at 03:24
  • I originally tried a return chain, but damn that was hell to try and manage. There's another answer that mentions throwing an exception as well, so I will try that, thanks. – Dwayne H Oct 24 '15 at 03:28
1

You can throw. An exception will clean up the unwound scope.

//...
int main()
{
  try{
    employee emp1;
    throw 1; //fake; throwing an object is more advisable in real situations
    cout << "Hello" << endl;
  }catch(int){ 
    exit(1); //or better simply `return 1;`
  }
}

Outputs:

Object destroyed
Petr Skocik
  • 58,047
  • 6
  • 95
  • 142
  • I'll have to look up a couple of those things. My actual project goes a few layers of functions deep, all of which ask for input, so would this idea be practical to work at any stage? Possibly as a generalised throw/exit function that can be called if they input exit? – Dwayne H Oct 24 '15 at 03:32
  • 1
    Exceptions shoot through as many layers as they need to until caught. And it's generally advisable to have a `try{}catch{}` block in your `main` function anyway. Might as well have it convert fatal exceptions to return values and simply `return`. No need to use `exit()` at all. – Petr Skocik Oct 24 '15 at 03:37
1

What I need to know is if a basic class object is destructed when I use exit().

You've demonstrated that it does not. The os service labeled 'exit' does so without concern about code issues. Note that exit existed before C++.

is there a way to have a program terminate without it screwing with memory?

You have demonstrated that exit is at least one way to terminate the program without calling a C++destructor. exit is language agnositic

a) This means the memory will not be modified by the destructor.

So is the memory screwed with?

b) Part of exit (and main return) processing is that all memory resources of that process will be reclaimed by the OS. The memory will not be 'screwed' with, (no destructor called, no 'wipe' or 'erase').

c) Part of exit is to close any streams open by that process. (Files, devices, terminals, etc.)

If b) or c) modify memory, you can not tell, because the modifications have no more association with the closed process.

2785528
  • 5,438
  • 2
  • 18
  • 20
  • Sorry, my meaning of being screwed with was a bit unclear. I was meaning in the sense of memory being used not being freed by calling destructors when an exit situation happens. – Dwayne H Oct 24 '15 at 03:40
  • @DwayneH If you exit, memory is always (forcibly) freed, unless you're on a very crappy operating system. – Petr Skocik Oct 24 '15 at 03:42
  • Well we're using Linux at uni, but I don't know if relying on that is a bad idea. Since we're being graded on a bunch of things including memory management, it might be safer to try one of the other options to keep them happy. – Dwayne H Oct 24 '15 at 03:49
  • 1
    @DwayneH Agreed. It's good to exit with a clean state (tools such as valgrind test for this), because that means your program's functionality can be safely integrated into a larger package. I'd advise against using non-const global/static variables, though. If you use those, your functions won't place nice in a multithreaded environment unless you have locks around those variables. Exceptions are the C++ mechanism intended for backing up with proper cleaning of objects. – Petr Skocik Oct 24 '15 at 19:18
  • @PSkocik I'm in the process of trying to get an exit function working that calls the destructs before using exit(), that way everything should be done properly. I'm just stuck on making a vector work to store everything created. The exit idea is just something I wanted to try, if I can't do it I'll just leave it off. – Dwayne H Oct 24 '15 at 23:11