DispatcherTimer dt = new DispatcherTimer();
dt.Interval = new TimeSpan(0, 0, 0, 0, 100);
dt.Tick += new EventHandler(dt_dt);
I have a question about the new
keyword. I have a DispatcherTimer which I set to an interval. Let’s say the user wants to change the interval.
dt.Interval = new TimeSpan(0, 0, 0, 0, 50);
So, what happens to the very first new TimeSpan
? Is it still there? Or does the new one override the previous? I don’t think it does.
And if I want to change the interval, is the new
keyword the only way to declare a new TimeSpan? I am asking this, since I’m not sure whether it’s actually okay or even right to declare a new TimeSpan every time the value changes.
In short: The new operator returns the unique address of the allocated object. When you allocate an array of objects the address of the first object is returned.
Memory that is dynamically allocated using the new operator can be freed using the delete operator. The delete operator calls the operator delete function, which frees memory back to the available pool. Using the delete operator also causes the class destructor (if one exists) to be called.
What happens when new fails? Explanation: While creating new objects, the new operator may fail because of memory errors or due to permissions. At that moment the new operator returns zero or it may throw an exception. The exception can be handled as usual.
New and Delete operators can be overloaded globally or they can be overloaded for specific classes.
You have class (DispatcherTimer
) which has field of type TimeSpan
, and TimeSpan
is a struct.
Since it's a struct - it's "embedded" into instance of DispatcherTimer
. So instance of DispatcherTimer
looks in memory like this:
<various metadata>...<contents of timespan>...
If it were class (reference type), it would look like this:
<various metadata>...<reference to timespan>...
When you do
dt.Interval = new TimeSpan( 0, 0, 0, 0, 50);
Instance of TimeSpan
is allocated (on stack in this case) and copied to the memory region of DispatcherTimer
instance allocated for Interval
, overwriting what was there before.
So we had
<various metadata>...<contents of timespan 1>
and now we have
<various metadata>...<contents of timespan 2>
That means old interval timespan is simply overwritten, it will not be collected by garbage collector because there is just nothing to collect (contrary to what accepted answer claims).
For that reason doing that in a tight loop is also not a problem (though of course there is no reason to). Consider this code:
class ClassWithRefField {
public TestClass Field;
}
class ClassWithStructField {
public TestStruct Field;
}
class TestClass {
public TestClass(int payload) {
Payload = payload;
}
public int Payload;
}
struct TestStruct {
public TestStruct(int payload)
{
Payload = payload;
}
public int Payload;
}
Then if you do:
static void Main(string[] args) {
var f = new ClassWithRefField();
while (true) {
f.Field = new TestClass(1);
}
}
And observe process memory even in process explorer in windows - you will see that memory constantly grows and drops. That's instances of TestClass
are created on heap and collected by garbage collector.
However if you do this:
static void Main(string[] args) {
var f = new ClassWithStructField();
while (true) {
f.Field = new TestStruct(1);
}
}
Memory in process explorer will stay absolutely constant, because the same region of memory is constantly overwritten, so there is nothing to collect. This loop can run forever.
And yes - it's ok to do it the way you are doing.
Well, there are multiple things to consider here. Yes, it does create a second instance of the TimeSpan
struct. Since the first one isn't referenced anywhere, it will go out of scope and will be cleaned up by the garbage collector. No harm done.
If TimeSpan
would have been a class, you probably change one of the properties, but it is a struct, and structs are usually immutable, meaning you can't change their value. (This is due to multiple reasons, I would suggest to read up on that)
So the only option you have here is to create a new TimeSpan
struct instance. That is no problem if you don't do it in a tight loop (creating a low of new instances in a very short time, consuming lots of memory).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With