home *** CD-ROM | disk | FTP | other *** search
- Newsgroups: comp.lang.c++
- Path: sparky!uunet!wupost!uwm.edu!linac!att!cbnewsk!pegasus!hansen
- From: hansen@pegasus.att.com (Tony L. Hansen)
- Subject: Re: delete with arrays - help please
- Organization: AT&T
- Date: Thu, 19 Nov 1992 16:48:00 GMT
- Message-ID: <1992Nov19.164800.707@cbnewsk.cb.att.com>
- Summary: always use delete[] with arrays of all types
- Keywords: c++, destructors, delete[], arrays
- References: <1992Nov18.181425.6817@gopher.dosli.govt.nz>
- Sender: hansen@cbnewsk.cb.att.com (tony.l.hansen)
- Lines: 69
-
- < From: carroll@sde.mdso.vf.ge.com (Carroll James)
- < (via From: srlncnc@gopher.dosli.govt.nz (Chris Crook))
- <
- < The reason for this is simple. new and delete really use 'malloc' and
- < 'free' (or similar systems calls to the heap manager) to allocate a bocks
- < of memory.
- <
- < The heap manager knows how big of a block has been allocated but it DOES
- < NOT know anything about data types in those blocks. Because of this the
- < call of the destructors is done in C++ and not by the 'system' (in this
- < case, the heap manager, which is part of the system).
- <
- < In older versions of C++ (2.0 ?) you couldnt use a [] without a number in
- < it because the delete operator (which is really a library routine in C++)
- < didnt get a count from the heap manager. The entire reason for the [n] was
- < for the delete operation to call the destructor 'n' times. In newer
- < versions of C++ the delete operator became smart enough to know (or to
- < figure out based on size of element being deleted and the size of the
- < block allocated) what 'n' is and call the destructor that many times.
- <
- < In either case (i.e. delete x, or delete [n] x) a call is made to 'free'
- < (which would look like free(x)) at which point the entire block is freed
- < by the heap manager. The problem is that for Object instancted with
- < destructors, the destructors will not all be called unless the [n] is
- < supplied (remember that delete without [] or [n] assumes there is only
- < one).
- <
- < For built in types or object instances that dont have destructors, the
- < total block of memory is freed. Therefore for these instances or built in
- < types the overall effect is the same for both 'delete x' and 'delete []
- < x'.
-
- There are other implementations of which you are evidently not aware for
- which this won't work.
-
- Consider this common implementation:
-
- Invoking "X *px = new X[10]" will invoke "operator new(sizeof(size_t) +
- sizeof(X)*10)". Into that returned address, the size of the array (10 in
- this case) will be placed into the first four (actually, sizeof(size_t))
- bytes. The function which handles "new X[10]" will then add four bytes
- to the address, invoke the 10 constructors, and then return that new
- address. That is, the address stored into px, as returned by "new
- X[10]", will be four bytes beyond that returned by the "operator new()".
-
- When "delete[] px" is invoked, delete[] will subtract four bytes from
- the address it's passed, retrieve the count, invoke the destructor on
- those objects, and pass the new address (px-4) to "operator delete()".
-
- (Most current implementations which use this scheme only do it if the
- class has a destructor, and don't store the count otherwise. But such an
- optimization is not required.)
-
- What happens if you invoke "delete px"? The value passed to "operator
- delete()" will NOT be an address that was returned from "operator new()"!
-
- Can you say "core dump"? I knew you could.
-
- < I think ARM mentions some precautions to take. I personally dont like
- < making a distinction between built in types and object instances when it
- < can be avoided but in this case it will work.
-
- This is all implementation dependent, and on some implementations you may be
- able to get away with just invoking "delete px". But don't count on it!
-
- Tony Hansen
- hansen@pegasus.att.com, tony@attmail.com
- att!pegasus!hansen, attmail!tony
-
-