www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - lame question

reply %u <lenochware gmail.com> writes:
Is it necessary free memory allocated for member of structure, like in C? I
suppose not (we have gc). Example:

struct BITMAP {
(...)
ubyte[] pixels;
}

BITMAP* bitmap = new BITMAP;
bitmap.pixels = new ubyte[100*100];
(...)

// delete bitmap.pixels; //not necessary?

delete bitmap;
Apr 18 2011
next sibling parent reply Francisco Almeida <francisco.m.almeida gmail.com> writes:
== Quote from %u (lenochware gmail.com)'s article
 Is it necessary free memory allocated for member of structure, like in C? I
 suppose not (we have gc). Example:
 struct BITMAP {
 (...)
 ubyte[] pixels;
 }
 BITMAP* bitmap = new BITMAP;
 bitmap.pixels = new ubyte[100*100];
 (...)
 // delete bitmap.pixels; //not necessary?
 delete bitmap;

Using new implies that the allocated memory will be managed by the GC. You shouldn't need to delete any pointers. Note, however, that the availability of GC does not exclude manual memory management. Especially when you use structs, which are preferably allocated on the stack. D supports RAII as well - with struct. If you want to include heap management in the resources allocation of BITMAP, it is advisable to use C-style malloc() and free() in the constructor and destructor.
Apr 18 2011
parent lenochware <lenochware gmail.com> writes:
I see...thanks for answer. And if I call "delete bitmap", it will be removed
immediatelly, or it doesn't matter and gc will remove it when it will start its
cycle?

So even ubyte[] pixels will be allocated on the stack ?? What is prefered method
to allocate large byte array, then? Should I use malloc?
Apr 18 2011
prev sibling next sibling parent spir <denis.spir gmail.com> writes:
On 04/18/2011 10:31 AM, %u wrote:
 Is it necessary free memory allocated for member of structure, like in C? I
 suppose not (we have gc). Example:

 struct BITMAP {
 (...)
 ubyte[] pixels;
 }

 BITMAP* bitmap = new BITMAP;
 bitmap.pixels = new ubyte[100*100];
 (...)

 // delete bitmap.pixels; //not necessary?

 delete bitmap;

No, you don't need to manually delete pixels, but also not the pointer. By the way, structs are constructed on the stack; only by using 'new' will it be on the heap, but you often don't need that. Conversely, if you want truely referenced and heap-allocated objects, you may want to use class instead of struct. A common exception may be for data structures made of possibly numerous "pointed" objects, such as linked lists or trees of struct nodes. There, you may want manually pointed struct objects. Denis -- _________________ vita es estrany spir.wikidot.com
Apr 18 2011
prev sibling parent reply "Steven Schveighoffer" <schveiguy yahoo.com> writes:
On Mon, 18 Apr 2011 04:31:26 -0400, %u <lenochware gmail.com> wrote:

 Is it necessary free memory allocated for member of structure, like in  
 C? I
 suppose not (we have gc). Example:

 struct BITMAP {
 (...)
 ubyte[] pixels;
 }

 BITMAP* bitmap = new BITMAP;
 bitmap.pixels = new ubyte[100*100];
 (...)

 // delete bitmap.pixels; //not necessary?

 delete bitmap;

It is not necessary, because pixels will be collected by the GC sometime in the future. It will *not* free pixel's data by calling delete on the BITMAP pointer. Just a note, you may be tempted to use a destructor do effect the above (as is done in C++ commonly), but this is a very big mistake. And one other note -- delete will eventually be deprecated. In order to free memory, you must use clear and GC.free. -Steve
Apr 18 2011
next sibling parent reply lenochware <lenochware gmail.com> writes:
== Quote from Steven Schveighoffer (schveiguy yahoo.com)'s article
 On Mon, 18 Apr 2011 04:31:26 -0400, %u <lenochware gmail.com> wrote:
 Is it necessary free memory allocated for member of structure, like in
 C? I
 suppose not (we have gc). Example:

 struct BITMAP {
 (...)
 ubyte[] pixels;
 }

 BITMAP* bitmap = new BITMAP;
 bitmap.pixels = new ubyte[100*100];
 (...)

 // delete bitmap.pixels; //not necessary?

 delete bitmap;

in the future. It will *not* free pixel's data by calling delete on the BITMAP pointer. Just a note, you may be tempted to use a destructor do effect the above (as is done in C++ commonly), but this is a very big mistake.

So what is "correct" way to manage structures like BITMAP? Don't bother with freeing memory at all?
 And one other note -- delete will eventually be deprecated.  In order to
 free memory, you must use clear and GC.free.
 -Steve

It's pity. I like delete.:)
Apr 18 2011
parent KennyTM~ <kennytm gmail.com> writes:
On Apr 19, 11 01:25, Graham Fawcett wrote:
 On Mon, 18 Apr 2011 11:38:56 -0400, Steven Schveighoffer wrote:

 On Mon, 18 Apr 2011 11:21:46 -0400, Graham Fawcett<fawcett uwindsor.ca>
 wrote:


 The recommended alternative to destruction is to use clear, since it
 runs the appropriate finalizers, plus sets it to null.

Thanks for that. The documentation for std.array.clear() is rather terse ("clears the managed array"), so your explanation is very helpful. Best, Graham

By 'clear' he means the global function 'clear' in object.di (It seems not documented on the digitalmars website), not std.array.Appender.clear(). https://github.com/D-Programming-Language/druntime/blob/master/import/object.di#L437
Apr 18 2011
prev sibling next sibling parent "Steven Schveighoffer" <schveiguy yahoo.com> writes:
On Mon, 18 Apr 2011 09:44:38 -0400, lenochware <lenochware gmail.com>  
wrote:

 == Quote from Steven Schveighoffer (schveiguy yahoo.com)'s article
 On Mon, 18 Apr 2011 04:31:26 -0400, %u <lenochware gmail.com> wrote:
 Is it necessary free memory allocated for member of structure, like in
 C? I
 suppose not (we have gc). Example:

 struct BITMAP {
 (...)
 ubyte[] pixels;
 }

 BITMAP* bitmap = new BITMAP;
 bitmap.pixels = new ubyte[100*100];
 (...)

 // delete bitmap.pixels; //not necessary?

 delete bitmap;

in the future. It will *not* free pixel's data by calling delete on the BITMAP pointer. Just a note, you may be tempted to use a destructor do effect the above (as is done in C++ commonly), but this is a very big mistake.

So what is "correct" way to manage structures like BITMAP? Don't bother with freeing memory at all?

In most cases yes. Freeing memory manually is dangerous (the compiler cannot verify that there are no other references to that memory), and should only be used when optimizing performance, or to workaround runtime deficiencies like false pointers. In essence, you should avoid freeing memory unless you know what you are doing. It's very possible you do know that it's OK. -Steve
Apr 18 2011
prev sibling next sibling parent Graham Fawcett <fawcett uwindsor.ca> writes:
On Mon, 18 Apr 2011 10:03:10 -0400, Steven Schveighoffer wrote:

 On Mon, 18 Apr 2011 09:44:38 -0400, lenochware <lenochware gmail.com>
 wrote:
 
 == Quote from Steven Schveighoffer (schveiguy yahoo.com)'s article
 On Mon, 18 Apr 2011 04:31:26 -0400, %u <lenochware gmail.com> wrote:
 Is it necessary free memory allocated for member of structure, like
 in C? I
 suppose not (we have gc). Example:

 struct BITMAP {
 (...)
 ubyte[] pixels;
 }

 BITMAP* bitmap = new BITMAP;
 bitmap.pixels = new ubyte[100*100];
 (...)

 // delete bitmap.pixels; //not necessary?

 delete bitmap;

sometime in the future. It will *not* free pixel's data by calling delete on the BITMAP pointer. Just a note, you may be tempted to use a destructor do effect the above (as is done in C++ commonly), but this is a very big mistake.

So what is "correct" way to manage structures like BITMAP? Don't bother with freeing memory at all?

In most cases yes. Freeing memory manually is dangerous (the compiler cannot verify that there are no other references to that memory), and should only be used when optimizing performance, or to workaround runtime deficiencies like false pointers. In essence, you should avoid freeing memory unless you know what you are doing. It's very possible you do know that it's OK.

Would "bitmap.pixels = null;" be a safe compromise? If you know you're not going to use "pixels" any more, this would mark it as reclaimable, but any other references to the array will keep it alive. Graham
Apr 18 2011
prev sibling next sibling parent "Steven Schveighoffer" <schveiguy yahoo.com> writes:
On Mon, 18 Apr 2011 11:21:46 -0400, Graham Fawcett <fawcett uwindsor.ca>  
wrote:

 On Mon, 18 Apr 2011 10:03:10 -0400, Steven Schveighoffer wrote:

 On Mon, 18 Apr 2011 09:44:38 -0400, lenochware <lenochware gmail.com>
 wrote:

 == Quote from Steven Schveighoffer (schveiguy yahoo.com)'s article
 On Mon, 18 Apr 2011 04:31:26 -0400, %u <lenochware gmail.com> wrote:
 Is it necessary free memory allocated for member of structure, like
 in C? I
 suppose not (we have gc). Example:

 struct BITMAP {
 (...)
 ubyte[] pixels;
 }

 BITMAP* bitmap = new BITMAP;
 bitmap.pixels = new ubyte[100*100];
 (...)

 // delete bitmap.pixels; //not necessary?

 delete bitmap;

sometime in the future. It will *not* free pixel's data by calling delete on the BITMAP pointer. Just a note, you may be tempted to use a destructor do effect the above (as is done in C++ commonly), but this is a very big mistake.

So what is "correct" way to manage structures like BITMAP? Don't bother with freeing memory at all?

In most cases yes. Freeing memory manually is dangerous (the compiler cannot verify that there are no other references to that memory), and should only be used when optimizing performance, or to workaround runtime deficiencies like false pointers. In essence, you should avoid freeing memory unless you know what you are doing. It's very possible you do know that it's OK.

Would "bitmap.pixels = null;" be a safe compromise? If you know you're not going to use "pixels" any more, this would mark it as reclaimable, but any other references to the array will keep it alive.

The recommended alternative to destruction is to use clear, since it runs the appropriate finalizers, plus sets it to null. If you delete bitmap, the runtime sets it to null already. So nothing would be referencing pixels. But yes, setting to null cannot ever hurt. It does not accomplish any freeing of memory immediately though. -Steve
Apr 18 2011
prev sibling next sibling parent Graham Fawcett <fawcett uwindsor.ca> writes:
On Mon, 18 Apr 2011 11:38:56 -0400, Steven Schveighoffer wrote:

 On Mon, 18 Apr 2011 11:21:46 -0400, Graham Fawcett <fawcett uwindsor.ca>
 wrote:
 
 On Mon, 18 Apr 2011 10:03:10 -0400, Steven Schveighoffer wrote:

 On Mon, 18 Apr 2011 09:44:38 -0400, lenochware <lenochware gmail.com>
 wrote:

 == Quote from Steven Schveighoffer (schveiguy yahoo.com)'s article
 On Mon, 18 Apr 2011 04:31:26 -0400, %u <lenochware gmail.com> wrote:
 Is it necessary free memory allocated for member of structure,
 like in C? I
 suppose not (we have gc). Example:

 struct BITMAP {
 (...)
 ubyte[] pixels;
 }

 BITMAP* bitmap = new BITMAP;
 bitmap.pixels = new ubyte[100*100];
 (...)

 // delete bitmap.pixels; //not necessary?

 delete bitmap;

sometime in the future. It will *not* free pixel's data by calling delete on the BITMAP pointer. Just a note, you may be tempted to use a destructor do effect the above (as is done in C++ commonly), but this is a very big mistake.

So what is "correct" way to manage structures like BITMAP? Don't bother with freeing memory at all?

In most cases yes. Freeing memory manually is dangerous (the compiler cannot verify that there are no other references to that memory), and should only be used when optimizing performance, or to workaround runtime deficiencies like false pointers. In essence, you should avoid freeing memory unless you know what you are doing. It's very possible you do know that it's OK.

Would "bitmap.pixels = null;" be a safe compromise? If you know you're not going to use "pixels" any more, this would mark it as reclaimable, but any other references to the array will keep it alive.

The recommended alternative to destruction is to use clear, since it runs the appropriate finalizers, plus sets it to null.

Thanks for that. The documentation for std.array.clear() is rather terse ("clears the managed array"), so your explanation is very helpful. Best, Graham
 
 If you delete bitmap, the runtime sets it to null already.  So nothing
 would be referencing pixels.
 
 But yes, setting to null cannot ever hurt.  It does not accomplish any
 freeing of memory immediately though.
 
 -Steve

Apr 18 2011
prev sibling next sibling parent "Steven Schveighoffer" <schveiguy yahoo.com> writes:
On Mon, 18 Apr 2011 15:17:11 -0400, KennyTM~ <kennytm gmail.com> wrote:

 On Apr 19, 11 01:25, Graham Fawcett wrote:
 On Mon, 18 Apr 2011 11:38:56 -0400, Steven Schveighoffer wrote:

 On Mon, 18 Apr 2011 11:21:46 -0400, Graham Fawcett<fawcett uwindsor.ca>
 wrote:


 The recommended alternative to destruction is to use clear, since it
 runs the appropriate finalizers, plus sets it to null.

Thanks for that. The documentation for std.array.clear() is rather terse ("clears the managed array"), so your explanation is very helpful. Best, Graham

By 'clear' he means the global function 'clear' in object.di (It seems not documented on the digitalmars website), not std.array.Appender.clear(). https://github.com/D-Programming-Language/druntime/blob/master/import/object.di#L437

That is a large omission! clear should be documented. I made a bugzilla report: http://d.puremagic.com/issues/show_bug.cgi?id=5855 -Steve
Apr 18 2011
prev sibling next sibling parent reply Timon Gehr <timon.gehr gmx.ch> writes:
Steven Schveighoffer wrote:
 And one other note -- delete will eventually be deprecated.  In order to
 free memory, you must use clear and GC.free.

 -Steve

Well, why? It seems like a bad decision to me.
Apr 19 2011
parent reply Andrei Alexandrescu <SeeWebsiteForEmail erdani.org> writes:
On 4/19/11 1:04 PM, Timon Gehr wrote:
 Steven Schveighoffer wrote:
 And one other note -- delete will eventually be deprecated.  In order to
 free memory, you must use clear and GC.free.

 -Steve

Well, why? It seems like a bad decision to me.

The feature is not going away, just the keyword. "delete" is a gratuitous carryover from C++, which had to invent it because the need for manual object disposal predated the introduction of templates. D stays a systems programming language but also has a safe subset and generally offers better safety guarantees than C++. It is excessive to allocate a keyword to a feature that's fundamentally unsafe, particularly since the underlying feature offers considerably fewer guarantees than its C++ counterpart. (Some GCs are unable to implement "delete" meaningfully.) Manual memory disposal for the GC heap will be implemented as a template function with semantics defined by the GC implementation. Andrei
Apr 19 2011
next sibling parent bearophile <bearophileHUGS lycos.com> writes:
Andrei:

 (Some GCs are unable to implement 
 "delete" meaningfully.)
 
 Manual memory disposal for the GC heap will be implemented as a template 
 function with semantics defined by the GC implementation.

Now the function(s) that replace "delete" are meant to be hints for the GC. In a system language that uses a GC you probably enjoy some different kinds of GC hints (as in CLisp GC). Bye, bearophile
Apr 19 2011
prev sibling parent reply lenochware <lenochware gmail.com> writes:
== Quote from Andrei Alexandrescu (SeeWebsiteForEmail erdani.org)'s article
 On 4/19/11 1:04 PM, Timon Gehr wrote:
 Steven Schveighoffer wrote:
 And one other note -- delete will eventually be deprecated.  In order to
 free memory, you must use clear and GC.free.

 -Steve

Well, why? It seems like a bad decision to me.

"delete" is a gratuitous carryover from C++, which had to invent it because the need for manual object disposal predated the introduction of templates. D stays a systems programming language but also has a safe subset and generally offers better safety guarantees than C++. It is excessive to allocate a keyword to a feature that's fundamentally unsafe, particularly since the underlying feature offers considerably fewer guarantees than its C++ counterpart. (Some GCs are unable to implement "delete" meaningfully.) Manual memory disposal for the GC heap will be implemented as a template function with semantics defined by the GC implementation. Andrei

Well, I don't understand internal architecture at all, but from user's point of view it would be good keep some simple and nice way to remove object. I like if I can have things under control - if I want.
Apr 20 2011
parent Jesse Phillips <jessekphillips+D gmail.com> writes:
lenochware Wrote:

 Well, I don't understand internal architecture at all, but from user's point of
 view it would be good keep some simple and nice way to remove object. I like
if I
 can have things under control - if I want.

clear(myObjectThatMustGo);
Apr 20 2011
prev sibling parent "Steven Schveighoffer" <schveiguy yahoo.com> writes:
On Tue, 19 Apr 2011 14:04:38 -0400, Timon Gehr <timon.gehr gmx.ch> wrote:

 Steven Schveighoffer wrote:
 And one other note -- delete will eventually be deprecated.  In order to
 free memory, you must use clear and GC.free.

 -Steve

Well, why? It seems like a bad decision to me.

I'm neutral on the subject, you'd have to ask Andrei. I rarely use delete anyways. -Steve
Apr 19 2011