-1

I wonder if this is a good way to do that to reset a pointer to null. I think so but I want to be sure. I work in basic C++ (not c++ 11; c++ 14, ...).

Example:

MyClass * myClass = new MyClass();

delete myClass;
myClass = NULL;

I thought the delete reset the pointer but actually, no. If the pointer has the value 0xb861708 after the "new", after the "delete" the value is always 0xb861708. The delete frees the memory but does not reset the pointer. The freed memory can therefore be used by the operating system but the pointer still points to the memory area. If after the delete we do myClass->SomeFunction(), it crashes (SIGSEGV) the program or worse the operating system.

That's why I used to reset pointers after a delete but wanted to know if that was the right way to do it.

Many thanks.

Jocelyn

Reset the pointer the right way after a delete.

HolyBlackCat
  • 78,603
  • 9
  • 131
  • 207
Jocelyn
  • 27
  • 1
  • 11
    Use `std::unique_ptr` instead of low-level memory primitives and you won't have to bother. – Quentin Jan 24 '23 at 13:56
  • 1
    Yes, this is ok. Would use `nullptr` instead of `NULL` in C++11 or newer. Why are you limiting yourself to C++98 in year 2023? – HolyBlackCat Jan 24 '23 at 13:56
  • 3
    Use `myClass = nullptr;` instead of `myClass = NULL;`. I'm not sure what you mean by **basic C++**. The C++ standard is currently at C++20, and soon C++23. – Eljay Jan 24 '23 at 13:58
  • There was a time when people were doing stuff like `#define SAFE_DELETE(x) delete x; x = NULL;`. Didn't like it then, don't like it now. – Friedrich Jan 24 '23 at 14:03
  • 1
    *If after the delete we do myClass->SomeFunction()* -- Then that is a bug in your program. Probably more wise to figure out why your program is going down the path of calling functions using invalid pointers to objects. If your code turns into a many lines with `if (ptr == nullptr) do something;` all over the code base, then that means there is a flaw in the design and/or logic somewhere. – PaulMcKenzie Jan 24 '23 at 14:04
  • A bit off-topic bu and I know most "old" C++ text books begin explaining new/delete. But it is best if you could write your code without pointers/new/delete at all. C++ has move semantics / [move constructors](https://en.cppreference.com/w/cpp/language/move_constructor) and containers to manage lifecycles of objects too. Pointers imo are really only necessary if your objects live for a shorter time then your program, and/or if you need dynamic polymorpishm (virtual function calls). Else Quentin is right use std::make_unique if you really need dynamic memory allocation. – Pepijn Kramer Jan 24 '23 at 14:04
  • It should be noted that dereferencing a null pointer is UB. So `myClass->SomeFunction()` is not okay if `myClass == nullptr`. – Friedrich Jan 24 '23 at 14:07
  • Unless you are going to continue using the pointer, and test its value for `nullptr`, there really is no point in setting it to `nullptr`, it is just as incorrect to dereference a `nullptr` as it is to dereference a *deleted* pointer and this is a huge area for mistakes to be made. What if you forget to set it to `nullptr`? Use `std::unique_ptr` instead. – Galik Jan 24 '23 at 14:17
  • If you delete the pointer [just before it goes out of scope](https://stackoverflow.com/a/1931132/17398063), nobody can use it anyway, so then it doesn't matter. You might ask yourself why the program keeps deleted pointers around. *That* is not good practice. – BoP Jan 24 '23 at 14:27
  • @Friedrich: Oh the irony of that being safe when `x` is an array. – Bathsheba Jan 24 '23 at 14:49
  • 1
    RAII was a thing long before smart pointers. It was never a cool thing to have raw owning pointers all over the place. They belong in a class that `delete`s them in the destructor. There is no point to assign something to a member pointer in a destructor. – 463035818_is_not_an_ai Jan 24 '23 at 14:51
  • @HolyBlackCat because it is an old project :( We use Pre-standard C++ version. – Jocelyn Jan 24 '23 at 15:12
  • @Jocelyn -- *because it is an old project* -- Well, my comment about checking your program logic seems (at least to me) to be a bit more important. If you are setting your pointer to NULL so that later, you are checking for null, then there are a few questions you need to ask yourself, and that is: Why check for null when the logic dictated that the pointer should have been set, thus no null check should have been required? Making pointers null as you are trying to do indicate a "bug in the logic flow" is being covered up, or at least, very convoluted logic that could be simplified. – PaulMcKenzie Jan 24 '23 at 16:13

1 Answers1

1

It's idiomatic to set pointers to NULL after freeing them in C because C does not have anything similar to smart pointers in C++.

If you were doing manual memory management in modern C++ with new and delete then setting your pointers to nullptr (not NULL) after deleteing them would make sense in certain contexts, but manual memory management is already bad practice in modern C++. Use the smart pointer types that take care of this for you.

Govind Parmar
  • 20,656
  • 7
  • 53
  • 85
  • 2
    Idiomatic? Tough to say when it makes use-after-free bugs hard to find. It's a trade-off either way, being able to find use-after-free bugs vs. not having the program run into UB if the sanitizer isn't enabled and there are null checks everywhere. – chris Jan 24 '23 at 14:09
  • "Idiomatic" doesn't mean "the best possible practice in all situations" it means "normal coding practice you expect to see" – Govind Parmar Jan 24 '23 at 14:11
  • 2
    Right, and I'd argue that you wouldn't just expect to see every pointer being nulled after use because people have valid reasons to avoid doing that. It's a choice that's going to differ across different software projects. – chris Jan 24 '23 at 14:12
  • @chris I never said otherwise - just that it's an idiom that wouldn't raise eyebrows in C code – Govind Parmar Jan 24 '23 at 14:23
  • 1
    I never understood nulling a pointer after delete. What is it supposed to do exactly? Give me an example of a bug where nulling a pointer fixes it. – Passer By Jan 24 '23 at 14:28
  • See [this question](https://stackoverflow.com/questions/21057393/what-does-double-free-mean) for more details – Govind Parmar Jan 24 '23 at 14:30
  • 1
    there are certain situations where `ptr = nullptr;` after `delete` makes sense. Though often it does not more than to create a false sense of security, ie it does more harm than good. If somewhere later you expect the pointer to equal `nullptr` then of course you should do it, but that does not make it "good practice" to do it always – 463035818_is_not_an_ai Jan 24 '23 at 14:34
  • 1
    a typical use of manual `delete` is on a member pointer in the destructor. It would be bad practice to assign `nullptr` to a member that cannot be read anyhow. – 463035818_is_not_an_ai Jan 24 '23 at 14:36
  • @463035818_is_not_a_number Edited my answer to remove the words "good practice" from it – Govind Parmar Jan 24 '23 at 14:36
  • @GovindParmar thanks for your answer but unfortunately I work on an old project in Pre-standard C++ version :( – Jocelyn Jan 24 '23 at 16:14
  • @Jocelyn: Pre-standard? Wow, we're celebrating a quarter century of C++ standardization soon. Before C++11 we had C++03 and C++98. It must be quite hard supporting a project that old. But if you do have at least C++98, then you can use boost smart pointers. – MSalters Jan 24 '23 at 16:30
  • @MSalters I absolutely agree with you. From my point of view we should at least use c++11 but unfortunately it's not me who decides. – Jocelyn Jan 25 '23 at 08:38