Search code examples
c++classnew-operatordelete-operator

How do you safely clear an object from memory (with attributes) which was created using the new keyword?


As far as I know on this topic, every "new" call needs a corresponding "delete" call to that object. So is this really correct?:

using namespace std;

class Box {
   public:
      double length;
      char letters_in_box[80];
};

int main() {
   Box *b = new Box;
   b->length = 2.0;
   b->letters_in_box = "Hello world";

   //Some code with b

   delete b;

   return 0;
}

Is the memory associated with the "length" double and "letters_in_box" array cleared with this?


Solution

  • Yes. When you delete b it deletes also letters_in_box array.

    But, for your b->letters_in_box = "Hello world"; you will get a compile error: "error C3863: array type 'char [80]' is not assignable"

    #include <memory> // For 'memcpy_s' (since C11)
    
    class Box
    {
    public:
        double length;
        char letters_in_box[80];
    };
    
    int main()
    {
        Box* b = new Box;
    
        b->length = 2.0;
        // b->letters_in_box = "Hello world"; ** Compile Error C3863: array type 'char [80]' is not assignable **
        memcpy_s(b->letters_in_box, sizeof(b->letters_in_box), "Hello world", sizeof("Hello world"));
    
        // Some code with b
    
        delete b;
    }
    

    MODERN C++

    A better practice than new is smart pointers, than for example you don't have to bother with delete in case of exception and at all:

    #include <memory> // For 'std::unique_ptr' and for 'memcpy_s'
    
    class Box
    {
    public:
        double length;
        char letters_in_box[80];
    };
    
    constexpr char my_text[] = "Hello world"; 
    
    int main()
    {
        auto b = std::make_unique<Box>(); // No need to delete
    
        b->length = 2.0;
        memcpy_s(b->letters_in_box, sizeof(b->letters_in_box), my_text, sizeof(my_text));
    
        // Some code with b
    }
    

    Also, (instead of C array) I prefer to use C++ array:

    #include <array>  // For 'std::array'
    #include <memory> // For 'std::unique_ptr' and for 'memcpy_s' 
    
    class Box
    {
    public:
        double length;
        std::array<char, 80> letters_in_box;
    };
       
    constexpr char my_text[] = "Hello world";
    
    int main()
    {
        auto b = std::make_unique<Box>(); // No need to delete
    
        b->length = 2.0;
        memcpy_s(&b->letters_in_box, b->letters_in_box.size(), my_text, sizeof(my_text));
    
        //Some code with b
    }
    

    --

    One last comment: Without a constraint to use char[], I would use std::string instead:

    #include <string> // For 'std::string'
    #include <memory> // For 'std::unique_ptr' 
    
    class Box
    {
    public:
        double length;
        std::string letters_in_box;
    };
    
    int main()
    {
        auto b = std::make_unique<Box>(); // No need to delete
    
        b->length = 2.0;
        b->letters_in_box = "Hello world";
    
        //Some code with b
    }