I would assume in the following that 'instance' being set to 'nullptr'
should cause the instance of myClass that was created to no longer have any
pointers pointing to it, and therefore be 'destroyed':
ref myClass
{
public:
myClass() {}
~myClass() {} // never called
!myClass() {} // never called
} ;
main()
{
myClass^ instance = gcnew myClass() ;
instance = nullptr ; // shouldn't this cause destruction?
}
However, as indicated, neither the destructor or finalizer get called when
'instance' is set to 'nullptr'. Is the object previously pointed to by
'instance' still around (.e., it still has memory resources)? Isn't having
all existing pointers to an object either being set to nullptr or going out
of scope cause the object to be destructed? If not, what am I missing here?
If so, why is neither the destructor or finalizer called?
For context, using VS C++.NET 2005 Express in /clr mode, I'm trying to count
(using a static class variable) the number of existing instances of myClass.
It is easy to count the creations (bump counter in each constructor), but
how do I count the destructions?
thanks in advance for responses! : )
[==P==] 9 1316
Peter... When a managed class is no longer reachable from root it is eligible
for garbage collection. You can force the garbage collector just as a test
case to force the call to Finalize. In your example you are not using stack
based semantics so the destructor will not be called. I wrote an artice here
that may be of help. http://www.geocities.com/jeff_louie/...estructors.htm
Jeff
"Peter Oliphant" wrote: I would assume in the following that 'instance' being set to 'nullptr' should cause the instance of myClass that was created to no longer have any pointers pointing to it, and therefore be 'destroyed':
ref myClass { public: myClass() {} ~myClass() {} // never called !myClass() {} // never called } ;
main() { myClass^ instance = gcnew myClass() ; instance = nullptr ; // shouldn't this cause destruction? }
However, as indicated, neither the destructor or finalizer get called when 'instance' is set to 'nullptr'. Is the object previously pointed to by 'instance' still around (.e., it still has memory resources)? Isn't having all existing pointers to an object either being set to nullptr or going out of scope cause the object to be destructed? If not, what am I missing here? If so, why is neither the destructor or finalizer called?
For context, using VS C++.NET 2005 Express in /clr mode, I'm trying to count (using a static class variable) the number of existing instances of myClass. It is easy to count the creations (bump counter in each constructor), but how do I count the destructions?
thanks in advance for responses! : )
[==P==]
Hi Jeff,
Thanks for the response! : )
Ok, got a few questions then. How do I "force garbage collection"? Don't
know exactly what 'stack semantics' are (in contrast to the code sample I
provided), could you provide an equivalent to my code that IS in stack
semantic form?
Are you saying that the resources for the object previously pointed to by
'instance' are still 'valid' (even though there is no way to get to it from
the code since no pointers to it exist anymore) until the 'garbage
collector' decides to start garbage collecting, at which point the resources
may be released if needed?
The big question is as follows: Is there any call to a class that indicates
that it has just become elligible for garbage collection (that is, no
pointers exist that point to it)? That is, something that would trigger in
the sample code I gave when the only (or last) pointer to the object is set
to nullptr?
[==P==]
"JAL" <JA*@discussions.microsoft.com> wrote in message
news:E5**********************************@microsof t.com... Peter... When a managed class is no longer reachable from root it is eligible for garbage collection. You can force the garbage collector just as a test case to force the call to Finalize. In your example you are not using stack based semantics so the destructor will not be called. I wrote an artice here that may be of help.
http://www.geocities.com/jeff_louie/...estructors.htm
Jeff
"Peter Oliphant" wrote:
I would assume in the following that 'instance' being set to 'nullptr' should cause the instance of myClass that was created to no longer have any pointers pointing to it, and therefore be 'destroyed':
ref myClass { public: myClass() {} ~myClass() {} // never called !myClass() {} // never called } ;
main() { myClass^ instance = gcnew myClass() ; instance = nullptr ; // shouldn't this cause destruction? }
However, as indicated, neither the destructor or finalizer get called when 'instance' is set to 'nullptr'. Is the object previously pointed to by 'instance' still around (.e., it still has memory resources)? Isn't having all existing pointers to an object either being set to nullptr or going out of scope cause the object to be destructed? If not, what am I missing here? If so, why is neither the destructor or finalizer called?
For context, using VS C++.NET 2005 Express in /clr mode, I'm trying to count (using a static class variable) the number of existing instances of myClass. It is easy to count the creations (bump counter in each constructor), but how do I count the destructions?
thanks in advance for responses! : )
[==P==]
Peter.... I have use GC.Collect to force garbage collection for testing only.
I have also thrown an exception in finalize to document that finalize is
being called as main is exited. As for stack based semantics it would look
like this:
RAII r; // thats it
When an object is unreachable it is not valid in the sense that its methods
can be invoked. There is no reference counting by the garbage collector, it
normally simply searches the tree from root when memory runs low and if an
object is not reachable from root the object it can be collected.
"Peter Oliphant" wrote: Hi Jeff,
Thanks for the response! : )
Ok, got a few questions then. How do I "force garbage collection"? Don't know exactly what 'stack semantics' are (in contrast to the code sample I provided), could you provide an equivalent to my code that IS in stack semantic form?
Are you saying that the resources for the object previously pointed to by 'instance' are still 'valid' (even though there is no way to get to it from the code since no pointers to it exist anymore) until the 'garbage collector' decides to start garbage collecting, at which point the resources may be released if needed?
The big question is as follows: Is there any call to a class that indicates that it has just become elligible for garbage collection (that is, no pointers exist that point to it)? That is, something that would trigger in the sample code I gave when the only (or last) pointer to the object is set to nullptr?
[==P==]
Aha, by george I think I've got it! :)
My main problem is that I got so use to 'old syntax' managed objects
requiring them to be instantiated by 'new'ing them into pointers. Didn't
realize the new /clr syntax allows for construction of non-pointer instances
('stack semantics'). Maybe the old syntax did to, but I kept getting a
compiler error if I tried to construct any other way (so I got use to doing
it this way always, except with things like 'int' and 'bool').That is, I
didn't realize that:
RAII r ;
was legal, I thought the only way to construct a managed object was like
this:
RAII^ r = gcnew RAII() ;
[ or, old syntax, RAII* r = new RAII() ; ]
One more question if you would be so kind. In order for the stack symantics
to be possible, doesn't it require the class have a default (i.e., no
parameter) constructor? Or, alternately, one would have to construct using a
valid constructor, ala (imagine the definition of call RAII is extended to
include a constructor of the form "RAII( int x)"):
RAII r(3) ;
Put simply, stack symantics still doesn't allow the creation of an object
instance without going though a valid public constructor, Yes?
[==P==]
"JAL" <JA*@discussions.microsoft.com> wrote in message
news:3F**********************************@microsof t.com... Peter.... I have use GC.Collect to force garbage collection for testing only. I have also thrown an exception in finalize to document that finalize is being called as main is exited. As for stack based semantics it would look like this:
RAII r; // thats it
When an object is unreachable it is not valid in the sense that its methods can be invoked. There is no reference counting by the garbage collector, it normally simply searches the tree from root when memory runs low and if an object is not reachable from root the object it can be collected.
"Peter Oliphant" wrote:
Hi Jeff,
Thanks for the response! : )
Ok, got a few questions then. How do I "force garbage collection"? Don't know exactly what 'stack semantics' are (in contrast to the code sample I provided), could you provide an equivalent to my code that IS in stack semantic form?
Are you saying that the resources for the object previously pointed to by 'instance' are still 'valid' (even though there is no way to get to it from the code since no pointers to it exist anymore) until the 'garbage collector' decides to start garbage collecting, at which point the resources may be released if needed?
The big question is as follows: Is there any call to a class that indicates that it has just become elligible for garbage collection (that is, no pointers exist that point to it)? That is, something that would trigger in the sample code I gave when the only (or last) pointer to the object is set to nullptr?
[==P==]
Peter... Glad to hear that. As I recollect, if you don't write any
constructor the compiler will write a no arg constructor for you and only no
arg instantiation will be allowed. If you write any constructor, then only
your explicit constructors are available. There is no default copy
constructor or assignment operator for use on stack based ref classes. If you
try to return a stack based object from a method, the compiler will complain.
"Peter Oliphant" wrote: Aha, by george I think I've got it! :) ... RAII r(3) ;
Put simply, stack symantics still doesn't allow the creation of an object instance without going though a valid public constructor, Yes?
[==P==]
ref MyRefClass
{
public:
MyRefClass() {}
~MyRefClass() {}
} ;
main()
{
MyRefClass instance;
// destructor ~MyRefClass() is called here
}
"bonk" wrote: ref MyRefClass { public: MyRefClass() {} ~MyRefClass() {} } ;
main() { MyRefClass instance; // destructor ~MyRefClass() is called here }
So, what the OP's example does? a memory leak?
main() { myClass^ instance = gcnew myClass() ; instance = nullptr ; // shouldn't this cause destruction? }
Regards,
--PA
I believe it doesn't create a memory leak, but instead frees up memory the
garbage collector may use when it decides to, but won't call the finalizer
or destructor UNTIL it decides to.
So it isn't a 'leak' in the sense that it's memory the system has 'lost' or
has allocated and won't free up, but is instead memory which the system is
still in control of and can be freed up when desired, and will be freed up
upon application closing. Leaks typical remain after the application has
been closed because the system thinks the memory is still being used and/or
has lost the ability to de-allocate it since no pointer to it exists.
In theory, no ref class can possibly leak, that's the whole purpose behind
garbage collection...
[==P==]
PS - I'm the OP, and my initials are PO....lol
"Pavel A." <pa*****@NOwritemeNO.com> wrote in message
news:3B**********************************@microsof t.com... "bonk" wrote: ref MyRefClass { public: MyRefClass() {} ~MyRefClass() {} } ;
main() { MyRefClass instance; // destructor ~MyRefClass() is called here }
So, what the OP's example does? a memory leak?
main() { myClass^ instance = gcnew myClass() ; instance = nullptr ; // shouldn't this cause destruction? }
Regards, --PA
Pavel... As written the storage on the heap will be released when the garbage
collector runs. However, this is not deterministic behaviour. You can still
have deterministic behaviour without stack based sematics if you are willing
to write code like:
RAII^ heaped= nullptr;
try
{
heaped= gcnew RAII();
heaped->SayHello();
Console::WriteLine(heaped->I);
}
finally
{
if (heaped != nullptr)
{
delete heaped;
heaped= nullptr;
}
}
But the stack based example is much simpler:
RAII r;
r.SayHello();
Console::WriteLine(r.I);
The destructor will be called even if an exception is thrown. So... this
smacks of a smart pointer, an exception safe object on the stack that
automagically releases resources newed on the heap.
"Pavel A." wrote: "bonk" wrote: ref MyRefClass { public: MyRefClass() {} ~MyRefClass() {} } ;
main() { MyRefClass instance; // destructor ~MyRefClass() is called here }
So, what the OP's example does? a memory leak?
main() { myClass^ instance = gcnew myClass() ; instance = nullptr ; // shouldn't this cause destruction? }
Regards, --PA This thread has been closed and replies have been disabled. Please start a new discussion. Similar topics
by: Lars Grøtteland |
last post by:
Hello!
I was able to compile my aplication in Managed /clr code.
How can I refere one form (Windows Form(.NET)) in my app. It's ok to add it,
but how can I go into that form? I was thinking of...
|
by: Michi Henning |
last post by:
I've been having problem with destructors in the context of having ported C# code
developed under .NET to Mono. What happens is that, on a dual-CPU machine, various
parts of the code crash randomly...
|
by: Edward Diener |
last post by:
I have a __value class which uses some legacy C++ code. So I wrapped the
legacy C++ code in another __nogc class and have a pointer to that class as
a member of my __value class. When the __value...
|
by: Peter Oliphant |
last post by:
In the 'old days', we could create a pointer to an instance of a variable
like so:
int i = 58 ;
int* i_ptr = &i ;
int j = *i_ptr ; // j = 58
Now, in /clr how do we do the same? That is,...
|
by: nicolas.hilaire |
last post by:
Hi all,
i'm not totally clear with some concepts about managed and unmanaged
code.
I'm asking myself some questions :
- i've a MFC app, i want to use the framework dotnet by switching to...
|
by: Greg |
last post by:
For all new desktop apps is managed/CLR recommended? I.e. Native MFC/Win32
not recommended in general for new desktop apps? Speaking in general, not
referring to exceptions (e.g. drivers)
--
Greg...
|
by: Bern McCarty |
last post by:
We upgraded a bunch of MEC++ code to C++/CLI about 10 months ago and we've
noticed that our images bloated quite a lot in the process. Upon
investigating I observed that when a /clr compiland...
|
by: Bern McCarty |
last post by:
We upgraded a bunch of MEC++ code to C++/CLI about 11 months ago and we've
noticed that our images bloated quite a lot in the process. Upon
investigating I observed that when a /clr compiland...
|
by: David K in San Jose |
last post by:
I'm using managed (CLR) C++ in VS2005 to create a Windows app that contains a form named "MyForm". In the code for that
form I'm trying to invoke some static functions by using an array of function...
|
by: Charles Arthur |
last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
|
by: Sonnysonu |
last post by:
This is the data of csv file
1 2 3
1 2 3
1 2 3
1 2 3
2 3
2 3
3
the lengths should be different i have to store the data by column-wise with in the specific length.
suppose the i have to...
|
by: Hystou |
last post by:
There are some requirements for setting up RAID:
1. The motherboard and BIOS support RAID configuration.
2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...
|
by: marktang |
last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
|
by: Hystou |
last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
|
by: Oralloy |
last post by:
Hello folks,
I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>".
The problem is that using the GNU compilers,...
|
by: jinu1996 |
last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven...
|
by: tracyyun |
last post by:
Dear forum friends,
With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each...
|
by: isladogs |
last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM).
In this session, we are pleased to welcome a new...
| |