Consider the portion of code below (please do not care about deleting the firstArray
and secondArray
):
int *firstArray = new int[10];
int *secondArray = new int[20];
firstArray = secondArray;
I have three questions here:
Is the expression
firstArray = secondArray;
safe even though they have two different sizes?ps: It seems the compiler (code::blocks) does not complain.
Now that
firstArray
andsecondArray
have the same address, what happens if I delete one of the arrays, is the other one deleted too?Why, when I delete the second one, the application crashes.
CodePudding user response:
A pointer is just a number that corresponds to some memory location.
Operator new T[N]
allocates a block of memory (of size N * sizeof(T)
) and gives you the address of the first element.
Operator delete[] (T*)
uses the value you pass to it to recall what memory was allocated and reclaims it for further allocations.
The expression firstArray = secondArray;
sets the value of firstArray
to the value of secondArray
(not unlike if they were just integers). From here on out both pointers point to the same memory (and the original value of firstArray
is forgotten).
When you subsequently delete[]
one of them, the memory that is pointed to by those pointers is freed (and the corresponding entry in the allocator is removed).
When you delete[]
the other pointer, the memory was already deleted, so the program will have undefined behavior and might crash.
And, of course, since the original value of firstArray
is forgotten, there is no way to delete it now - there is a memory leak.
CodePudding user response:
Okay, let's talk about what you're doing here.
- Is it safe? Yes. But it's a mistake because you have orphaned the data that secondArray used to point to. They now point to the same space in memory.
Imagine that firstArray holds the memory address 0x1000 and secondArray holds address 0x2000. After this assignment, they both hold 0x1000, and 0x2000 is orphaned.
If you delete [] firstArray, then continuing to reference 0x1000 by either pointer can lead you into trouble. You're going to step all over who knows what.
You've now engaged in undefined behavior, and crashes are common when you engage in undefined behavior.
Now, here's some opinion. It's important to understand the underlying memory systems, but once you do, start using various smarter containers. You can use std::array instead, for instance, and then you don't have to deal with memory allocation at all. This eliminates huge classes of bugs.