Does calling new [] twice on the same pointer without calling delete [] in between cause a memory leak?

后端 未结 6 1012
天命终不由人
天命终不由人 2021-01-25 19:21

I\'ve heard that you should usually \"delete\" whenever you use \"new\", yet when I run a simple test program (below), it doesn\'t seem to make a difference which numbers I put

相关标签:
6条回答
  • 2021-01-25 19:53

    Yes. Fortunately, there's a better way -- instead of allocating the memory directly, use std::vector:

    #include <iostream>
    #include <vector>
    
    int main()
    {
        double *array;
        const int arraySize = 100000;
        const int numLoops = 100000;
    
        for (int i = 0; i < numLoops; i++)
        {
           std::vector<double> array(arraySize);
           // use it just like a normal array
        }
    
        int x;
        std::cin >> x; // pause the program to view memory consumption
        return 0;
    }
    

    The vector will be destroyed (and the memory it controls released) each iteration of the loop.

    You shouldn't generally use new unless you really need to. I'd go so far as to say there's never a need (or even good reason) to use the array form of new.

    0 讨论(0)
  • 2021-01-25 19:58

    No, it's not sufficient.

    Each time you call new or new[], some memory is allocated, and you are given the address of that memory (in order to be able to use it). Each piece of memory must eventually be deleted (or delete[]d).

    You are storing that address in array, but then immediately overwriting it on the next iteration. Therefore you have no way of delete-ing all of pieces of memory that you've been allocated. Therefore you have a memory leak.

    0 讨论(0)
  • 2021-01-25 20:03

    Two questions, two answers.

    Question one: Does calling new [] twice on the same pointer without calling delete [] in between cause a memory leak?

    Answer one: Not always, but 99% of the time yes. The code below calls new twice, with the pointer to array, but the first time it assigns the address of the allocated memory to array2, and the second time it keeps the address to itself. It is possible to delete both array in this scenario.

    #include <iostream>
    
    int main()
    {
        double *array;
        double *array2;
        const int arraySize = 100000;
    
        for (int i = 0; i < 2; i++)
        {
            // do I need to call "delete [] array;" here?
            array = new double[arraySize];
            if(i == 0)
            {
                array2 = array;
            }
        }
    
        int x;
        std::cin >> x; // pause the program to view memory consumption
    
        delete [] array;
        delete [] array2;
    
        return 0;
    }
    

    Question Two: Is this usage of delete [] sufficient?

    Answer Two: no, because the delete call only influences the address pointed to by the pointer you've given it. As you overwrote the pointer in your example, it deletes the last allocated section of memory

    0 讨论(0)
  • 2021-01-25 20:10

    It helps to understand correctly what you are actually doing.

    You are not calling new[] twice on the same pointer. You are calling new[] twice, and storing both results into the same pointer. new[] simply returns a pointer to the allocated memory. To avoid leaking memory, you have to free that memory again at some point. But the pointer is not the memory, it is just a pointer telling you where the allocated memory is.

    So you can always overwrite the pointer, setting it to point to a new, different address. And then you just lost all knowledge of where it used to point to. If it used to point to memory that you ought to free, then you can no longer find that chunk of memory, so you can no longer call delete[] on it, and so... it is leaked.

    0 讨论(0)
  • 2021-01-25 20:11

    Yes. You don't call new on a pointer, you call new and it returns a pointer to the allocated memory. You are responsible for holding onto that pointer and deleting it. If you overwrite that value, as you are, you are leaking.

    0 讨论(0)
  • 2021-01-25 20:18

    Whenever you new (or new[]) memory you must delete (or delete[]) it or it will leak.

    Each time you call new you get returned a pointer to the heap allocated object if the new operation succeeds. If the pointer to this memory goes out of scope or is reassigned (i.e. what you are doing here) then you will be unable to delete the memory later.

    In your code example, only the last allocated memory will be destroyed. You can use something like process explorer or even task manager to check for memory leaks.

    0 讨论(0)
提交回复
热议问题