www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - Strict capacity of array

reply "FreeSlave" <freeslave93 gmail.com> writes:
Suppose some class contains slice (dynamic array) as data member. 
Constructor takes integer value that defines the size of data 
should be allocated. After object was constructed size of slice 
never changes by design.

Dynamic arrays are allocated with extra space that we can know 
from 'capacity' property. But how can I allocate exactly as much 
elements as I want? Because in case described above we don't need 
extra space.

I know it's possible to use malloc in constructor and free in 
destructor. But what if I want to expose inner slice by shallow 
copy (i.e. by copying pointer and size, but not underlined data) 
then use it just like usual dynamic array whose lifetime does not 
depend on lifetime of an object it belongs and is managed by GC?
Dec 13 2013
next sibling parent =?UTF-8?B?QWxpIMOHZWhyZWxp?= <acehreli yahoo.com> writes:
On 12/13/2013 10:47 AM, FreeSlave wrote:

 Suppose some class contains slice (dynamic array) as data member.
 Constructor takes integer value that defines the size of data should be
 allocated. After object was constructed size of slice never changes by
 design.

 Dynamic arrays are allocated with extra space that we can know from
 'capacity' property. But how can I allocate exactly as much elements as
 I want? Because in case described above we don't need extra space.
If it is not maintained by you, you can never be sure. There is arr.reserve(N) that ensures that much room without placing .init elements on the space.
 I know it's possible to use malloc in constructor and free in
 destructor. But what if I want to expose inner slice by shallow copy
 (i.e. by copying pointer and size, but not underlined data) then use it
 just like usual dynamic array whose lifetime does not depend on lifetime
 of an object it belongs and is managed by GC?
That is supported: auto slice = rawPtr[0..number_of_elements]; Ali
Dec 13 2013
prev sibling parent reply Marco Leise <Marco.Leise gmx.de> writes:
Am Fri, 13 Dec 2013 19:47:34 +0100
schrieb "FreeSlave" <freeslave93 gmail.com>:

 Suppose some class contains slice (dynamic array) as data member. 
 Constructor takes integer value that defines the size of data 
 should be allocated. After object was constructed size of slice 
 never changes by design.
 
 Dynamic arrays are allocated with extra space that we can know 
 from 'capacity' property. But how can I allocate exactly as much 
 elements as I want? Because in case described above we don't need 
 extra space.
There was a recent discussion about the capacity of a dynamic array that is allocated with a known size (e.g. new int[](25)). I think the extra space comes from the way the GC allocates blocks of memory in preset sizes. Actually a malloc implementation could also have some hidden overallocation.
 I know it's possible to use malloc in constructor and free in 
 destructor. But what if I want to expose inner slice by shallow 
 copy (i.e. by copying pointer and size, but not underlined data) 
 then use it just like usual dynamic array whose lifetime does not 
 depend on lifetime of an object it belongs and is managed by GC?
Have you tried this?: import core.memory; int[] data = (cast(int*)GC.malloc(size * int.sizeof, GC.BlkAttr.NO_SCAN))[0 .. size]; -- Marco
Dec 13 2013
parent reply "FreeSlave" <freeslave93 gmail.com> writes:
Thanks for answers.

On Friday, 13 December 2013 at 19:35:01 UTC, Marco Leise wrote:
 Have you tried this?:

 import core.memory;
 int[] data = (cast(int*)GC.malloc(size * int.sizeof, 
 GC.BlkAttr.NO_SCAN))[0 .. size];
Did you mean GC.BlkAttr.NONE maybe? If I get it right GC.BlkAttr.NO_SCAN means that memory will never be collected by GC (i.e. it's just like C malloc), but I've asked for opposite.
Dec 13 2013
parent Marco Leise <Marco.Leise gmx.de> writes:
Am Fri, 13 Dec 2013 21:02:58 +0100
schrieb "FreeSlave" <freeslave93 gmail.com>:

 Thanks for answers.
 
 On Friday, 13 December 2013 at 19:35:01 UTC, Marco Leise wrote:
 Have you tried this?:

 import core.memory;
 int[] data = (cast(int*)GC.malloc(size * int.sizeof, 
 GC.BlkAttr.NO_SCAN))[0 .. size];
Did you mean GC.BlkAttr.NONE maybe? If I get it right GC.BlkAttr.NO_SCAN means that memory will never be collected by GC (i.e. it's just like C malloc), but I've asked for opposite.
You got it wrong :) NO_SCAN means that the memory block you allocate isn't scanned for _more_ references to stuff on the GC heap. If you use the allocated memory as an int[] it doesn't make sense to look into it for pointers to other memory blocks in order to mark them alive. (The GC is a mark&sweep algorithm.) If you actually store class pointers or similar instead of ints then drop that attribute. -- Marco
Dec 13 2013