Delete a pointer passed to a function?

Started by
14 comments, last by Ravyne 14 years, 8 months ago
If you pass a pointer to a function in Cpp, should it be deleted explicitly at the end of the function, or will it go out of scope and be deleted by it-self freeing the memory? Example:

void myFunction(MyObjectType *anObject)
{
...
// do some stuff
...

// now delete the pointer?
delete anObject;
}

Thanks
Advertisement
No automatic call of delete will be performed.
When things go out of scope, their destructors are called.

Destructors for primitive types do nothing. Pointers are primitive types. Thus, the pointed-at thing will not have 'delete' called on it.

This is a good thing, because many pointers should never have 'delete' called on them. You only call 'delete' to deallocate things that were allocated with 'new', and only once per allocation. Remember, 'delete' cleans up the pointed-at thing, not the pointer. The pointer requires no cleanup itself.
And if you want a function to delete an incoming pointer you should do it this way to allow the function not only to delete the object but also modify the variable that you provided as function parameter to carry information about this deletion to the outside of the function:

void myFunction(MyObjectType *anObject){...// do some stuff...// now delete the pointer?delete anObject;}void myOtherFunction(){   MyObjectType *mo = new MyObjectType();   myFunction(mo);   // <- here mo still looks like a valid pointer because it still points to the address but the instance is already deleted}


So this is how to write functions that should also modify the address variables (pointers) you hand in to the functions:


void myFunction(MyObjectType **anObject){...// do some stuff...// now delete the pointer?delete (*anObject);(*anObject) = NULL;}void myOtherFunction(){   MyObjectType *mo = new MyObjectType();   myFunction(&mo);   // <- here mo is NULL and you know it is no longer pointing to a valid object}
------------------------------------I always enjoy being rated up by you ...
Ok thank you very much. So what I understand is that I have to be careful when deleting pointers. As Waterwalker said if I delete an incoming pointer into a function inside the function I may not be able to use the object if it was instantiated outside of the function since it would be gone because I called delete on it. Also thanks to Zahlman for describing that pointers are primitives, I didn't know that.

The only thing I could comment is Waterwalker's code at the very end:

delete (*anObject);
(*anObject) = NULL;

There is no need to do the second line since like Zahlman said the pointer will be gone once it goes out of scope. Although the two lines show how to get rid of pointers to pointers, if need be. But I am not sure if it's right. I though to delete a pointer to a pointer you have to do something like this:

delete (*anObject);
delete anObject;

Since first you delete the object it-self by the first line and then you delete the middle object (pointer) by the second line. And the pointer to the pointer will be gone by it self once it goes out of scope. Or do I just need to do ONLY the second line to delete the object AND the middle pointer?

Thanks again.
Quote:Original post by Flopid
Since first you delete the object it-self by the first line and then you delete the middle object (pointer) by the second line. And the pointer to the pointer will be gone by it self once it goes out of scope. Or do I just need to do ONLY the second line to delete the object AND the middle pointer?


No, the pointer itself is a local variable so it makes no sense to call delete on it - it is automatically destroyed when its scope exits. The object that is pointed to is dynamically allocated on the heap, so that needs to be deleted.

void f(int *i){    delete i; // this deletes the object pointed to by i}void g(){    int *x=new int(23); // x is a local variable, but is pointing to dynamically allocated memory    f(x);    // at this point the memory pointed to by x has been deleted    // scope exits, so the local variable x is destroyed}


Either way, it would be a very bad design to have a function delete memory that was passed to it. If someone were to do, for example:

void h(){    int z;    g(&z);    int y=z+10;}


then you are into undefined behaviour and anything could happen. The compiler cannot catch this.

Are you just trying to understand how pointers and dynamic allocation works, or is there something specific you are trying to do? We very rarely call delete explicitly in modern C++.
Quote:Original post by Flopid
There is no need to do the second line since like Zahlman said the pointer will be gone once it goes out of scope.

Yes there is nedd. The pointer does only store a memory address to the object you have allocated with new. So you can call delete on the address stored in the pointer. This delete cleans up the memory but the pointer does still point to the address in memory. And if you access it after deleting the object stored there all kind of weird thigs start to happen with crashes being the best possible outcome that straight away tells you that you have failed [grin]

And since the pointer was in this particular example handed in to the function as parameter it does not loose scope at the end of the function.
------------------------------------I always enjoy being rated up by you ...
Quote:Original post by Waterwalker
Quote:Original post by Flopid
There is no need to do the second line since like Zahlman said the pointer will be gone once it goes out of scope.

Yes there is nedd. The pointer does only store a memory address to the object you have allocated with new. So you can call delete on the address stored in the pointer. This delete cleans up the memory but the pointer does still point to the address in memory. And if you access it after deleting the object stored there all kind of weird thigs start to happen with crashes being the best possible outcome that straight away tells you that you have failed [grin]


The point is, if you are organizing your code properly, it is impossible to access the invalid pointer, because there is no longer a variable in scope which corresponds to that pointer.

It is generally held that the only sane way to keep track of this memory management stuff is to have everyone clean up their own mess. Thus, functions clean up memory they allocate; they don't clean up allocated memory that was handed to them. Instead, whoever handed over the memory cleans it up afterward.

And by the way, you might want to look up this thing called "passing by reference". In modern C++, we use references where we can and pointers where we have to.
Theres also the option of using smart poitners (such as boost::shared_ptr) which take care of cleaning themselves up. Strongly recommend learning normal pointers first though.

someone has mentioned passning a poitner to a pointer and thats a good idea but does make your function code rather confusing later on with dereferances everywhere. You could pass a pointer by reference instead, its doing the same thing but a little neater code wise

int *test = new int;*test = 5;Func(test);// test should be NULL nowvoid Func(int *&in){    cout << *in;    delete in;    in = NULL;}

Interested in Fractals? Check out my App, Fractal Scout, free on the Google Play store.

Quote:Original post by Aardvajk

Are you just trying to understand how pointers and dynamic allocation works, or is there something specific you are trying to do? We very rarely call delete explicitly in modern C++.


Hmm well I just needed to pass an address into a function so it doesn't make a copy of the object which I need to use. Just though a pointer would get the job done. I am just not going to call delete inside the function, but outside when I need to get rid of the object.

Thnx

This topic is closed to new replies.

Advertisement