Chapter 7: Object Lifetime

Chapter 7: Object Lifetime

Introduction

C# language programming supports the object-oriented paradigm. It means that almost all operations in this programming language are based on objects and the operations executing by them. So it is vital to be aware of their creation, destruction and the way they use the limited source named memory.

In the 7th chapter of the "Programming C# 5.0" book, I have studied the object lifetime and the Garbage Collection mechanism (GC). GC is an important procedure to collect the dead objects as garbage and freeing up the memory space for efficient execution of our applications.

Garbage Collector

The CLR knows about all functions occurring in the memory. It knows about all variables, and the amount of memory using by them. It could track the alive and dead objects. CLR is responsible for creating the objects and allocating their need memory from the managed resources. But if there is not any sufficient space for that new object, the CLR decides to send a request to the OS to allocate a new space or reclaim the memory occupied by the dead objects.

One of the important points is that the CLR must be able to recognize the reachable and unreachable objects at first. The reachable objects tend to live longer and will be used or are being used by the application. But the unreachable objects are no longer in use so their memory could be freed. Reachable or non-reachable objects could be recognized through the root variables.

Roots are like live variables, static fields, objects which are created as a result of evaluating expressions and need to be alive until the end of some procedure. The GCHandle that lets you create a root object explicitly to give access to some objects to use the unmanaged resources could be considered as a root too. COM wrapper objects and pointers as the result of unmanaged resource calls could be considered as implicit roots as well.

Garbage collector releases the memory of different objects in multiple generations, based on their usage duration. It also tries to remove multiple free fragmentations between the occupied ones. Although the GC is an automatic mechanism that is under the control of the CLR, but sometimes it needs to be forced by the programmers.

Forcing garbage collector

The System.GC has a method called Collect (). We can call this method in case of emergency to release the unmanaged resources which do not call the garbage collector automatically. If you pass a number to this method it just collects the garbage of that generation and if you invoke it without any numbers, then it releases the dead objects of all generations.

Garbage collection considers a reasonable time to do the collection, so forcing it to collect the dead objects could cause some problems. In fact, it forces the GC to run too often and every time it may put much effort into occupying the CPU itself.

So when we, as programmers, know that the execution of the specific process is finished (or it is about to be useless for some hours or will not be used by the other processes), and it has not triggered the GC to release the memory, it needs to force the GC for cleaning up the memory!

Finalizers and Destructors

Constructor and destructors are two methods in any classes which decide about the birth and death of an object. They both have the same name as the class name. When the constructor is invoked, the CLR tries to allocate a block of memory to that reference type or object. And when the objects executions are finished, the CLR uses the GC to invoke the finalizer (another name of the destructor) to release its memory.

The finalizer, calls the finalize() method of the object's base class implicitly, and the programmer has no control over the finalizer. But for running the destructors, we have to be sure that the object is not reachable.

IDisposable

The GC have access to the managed resource, but it is not clear that when they would be triggered. There is not any guarantee that the GC will invoke the destructors to free up the allocated space repeatedly.

So how to release the unmanaged memory like the open files and streams? One way to be sure that we could release the unmanaged memory space is by implementing the IDisposable interface.

It is a mechanism for freeing up unmanaged resources. Any classes or interfaces inherit from this interface, should implement the Dispose() function. This function will be invoked by the objects occupying the unmanaged resource which are not needed any more. For this purpose, we should wrap up the managed object in a SafeHandle or override the Object.Finalize() function of the base object class.

Boxing

Boxing and Unboxing are two important features of the C# programming language. These two operations help us to treat a value type as a reference type.

Boxing is the conversion of the value type to the type object. In fact, the CLR wraps the value type inside the System.Object instance and puts it on the managed heap. Unboxing is exactly the opposite of this procedure.

Boxing procedure copies the value of the value type implicitly in the type object. In this procedure, there has been created a reference type on the stack referring to the boxed value on the heap which contains the value type in it. This operation could be explicitly but it is never required.

But boxing and Unboxing is two expensive operations for the CLR. They could cause some problems for GC as well by producing boxes as garbage and some semantic difficulties during the execution.

Note: The materials of this article are adapted from the "Programming C# 5.0", Microsoft documents, and the CSharp-corner website.



要查看或添加评论,请登录

Elahe Dorani的更多文章

  • What's new in C# 8.0?

    What's new in C# 8.0?

    Introduction C# as a type-safe, object-oriented and component-oriented programming language is at the heart of the .Net…

  • What's new in C# 7.0 through 7.3?

    What's new in C# 7.0 through 7.3?

    Introduction In C# version 7.0 which is released within Visual Studio 2017, we are facing some newer and cooler…

  • What is new in C# 6.0?

    What is new in C# 6.0?

    In the 6.0 version of the C# programming language, the main focus of language designers were on adding some features to…

    1 条评论
  • Chapter 18: Asynchronous Language Features

    Chapter 18: Asynchronous Language Features

    Introduction The CPU of digital gadgets are the brain of devices. The operating systems on them would consider an…

    1 条评论
  • Chapter 10: LINQ

    Chapter 10: LINQ

    Introduction LINQ, the Language Integrated Query, is an integrated set of technologies using to apply some queries on…

    3 条评论
  • Chapter 9: Delegates, Lambdas, and Events

    Chapter 9: Delegates, Lambdas, and Events

    Introduction Delegates are some types that provide a reference to the methods. Events are some notification occurred in…

  • Chapter 8: Exceptions

    Chapter 8: Exceptions

    Introduction In the execution process of any programs, there could occur some errors and it is on the CLR decide to run…

  • Garbage Collection

    Garbage Collection

    The garbage collector is an automatic mechanism to detect and collect the dead object’s memory space and make it…

  • Chapter 6: Inheritance

    Chapter 6: Inheritance

    C# as an object-oriented language has some essential features which make it possible to produce object-oriented…

  • chapter 5: Collections

    chapter 5: Collections

    Introduction The data is the main concept we want to deal with in every program we write. The most important thing we…

社区洞察

其他会员也浏览了