• Skip to primary navigation
  • Skip to main content

Nikhil Mittal

|| Software Developer || App Developer ||

  • Home
  • About Me
  • Blog
  • Testimonials
  • Achievements
  • Portfolio
  • Interview Q&As
    • Angular – QA Series 1
    • Angular – QA Series 2
    • Angular – QA Series 3
    • Angular – QA Series 4
    • Convert Angular App to Mobile APK
    • C# TYPICAL QUESTIONS – SERIES
    • Advanced Q & A – Series 1
    • Advanced Q&A – Series 2
    • Advanced Q&A Series – 3
  • Free Video Tutorials
    • ASP.NET C#
    • C# Tutorial – In Hindi
    • C# Tutorial – English
    • C#-Advanced
    • MVC DOT NET 4.8
    • Web API Dot Net Core 3.1
    • Azure DevOps
    • HTML/CSS – In Hindi
    • SQL Developer
    • Angular 10+
    • Corporate Skills
  • Consulting
  • Contact Us

Advanced Q&A – Series 2

MEMORY MANAGEMENT – STACK / HEAP 

How memory is managed in .Net? 

I studied many articles about memory management, but they are all confusing about when memory is allocated in the stack and when memory is allocated in the heap. But I always got confused. But finally, I got exactly what I wanted.

Hopefully this article will help some of my friends who are still confused about the Stack and Heap.

In a simple way I can say that ….

As we know the Common Language Runtime (CLR) automatically handles Memory Management with the help of its components. Component one is the Garbage Collector which plays an important role in Memory Management. It contains two methods (Dispose and Finalize). Objects are automatically freed when they are no longer needed by the application through Garbage Collector.

When the Garbage Collector will be called to clean up unnecessary objects from memory. Non deterministic finalization is performed when the CLR foresees a memory deficiency.

How memory is managed for Value Type:

MemMgmt1.gif

In above figure you can see what happens in first two statements, simple value of variable a and b is storing in stack, now let’s see what happen in 3rd and 4th statement.

MemMgmt2.gif

As we can see that simply changes the position where the variable is actually stored. So in these statements we can see that there is no use of Heap.

Now we will just see for Reference Type:

class Program
{
    public int value;

    static void Main(string[] args)
    {
        Program prog = new Program();
        prog.value = 100;
        Program prog1 = prog;
        prog1.value = 200;
    }
}

Now let’s see how value will store in stack and heap in reference type.

Now we can see here for first statement…

MemMgmt3.gif

Now we will see for next two statements:

Program prog1 = prog;
prog1.value = 200;

MemMgmt4.gif
(Memory address for value 100) (Value)

Now we can see that the address is transferred from prog to prog1, and address is same so the value of that particular address is going to change as change is having on address so the value will be overriden in the Heap.

Hope you have gotten idea that how exactly reference type stores the value….

Now finally I will talk about very important thing that is how exactly string stores:

MemMgmt5.gif

class Program
{
    static void Main(string[] args)
    {
        string s = “Hello”;
        string ss = s;

        s = s + ” ” + “and Welcome”;
        Console.WriteLine(s);
        Console.WriteLine(ss);
        Console.ReadKey();
    }
}

Now we will see how value will store for this program:

For first statement:

string s = “Hello”;

MemMgmt6.gif

For second statement…

string ss = s;

MemMgmt7.gif

In this diagram we can see that the address is transferred from s to ss, so as well as the value will also be transferred to ss, so in heap value will be overriden.
Now come for the next statement….

s = s + ” ” + “and Welcome”;

MemMgmt8.gif

As in this image we can see that, as we just add “and welcome” in string “s”, then the value is changed at the address but in the heap hello will be at it’s own position so the value will not be overriden, and the new value of “s” will be stored at the new address which is here 6000. So now the address also will change for “s”, now the new address for “s” is 6000.

Hope you understand that how exactly value stored in stack and heap…

MUTABLE / IMMUTABLE CONCEPT:

Immutable String in C#

Immutable string cannot be changed once declared and defined. In a simple word, if we declare a string for example, string str = “interview”, a memory will be allocated for it and “interview” string will be placed in the memory.

If we try to change the string pointed by str variable e.g. str = “ interview sansar”, an another new memory will be created and “interview sansar” string will be placed in it. Now, str  variable will no longer point the memory where string “interview” was placed and old memory will be destroyed by GC.

Immutable string – C# program example:

You might be thinking that if we append a string or assign a string to variable str then just another memory is getting created because of immutable properties of string and older one is getting collected by GC and destroyed, then what is the advantage of immutable string in C# programming language.

Read another interview question benefits of immutable string in CSharp.

C# mutable string

C# mutable string means a string in a memory can be changed or modified and no new memory will be created on appending a string. We can use string builder class to create a mutable strings in c# programming.

C# Code Example – Mutable string using StringBuilder class

1234567891011121314151617181920  class MutableString    {        static void Main(string[] args)        {            //String builder will create a memory and place            //the string into memory.             //When we append the string same memory will be modified.            StringBuilder str = new StringBuilder(“interview”);            str.Append(“sansar”);            str.Append(“.com”);            Console.WriteLine(str);            //Output: interviewsansar.com                               }          }  

Conclusion: Difference between immutable and mutable string in C# language is that immutable string cannot be modified and mutable string can be modified at a memory location.

What is Garbage Collection and Why We Need It?

When you create any object in C#, CLR (common language runtime) allocates memory for the object from heap. This process is repeated for each newly created object, but there is a limitation to everything, Memory is not un-limited and we need to clean some used space in order to make room for new objects, Here, the concept of garbage collection is introduced, Garbage collector manages allocation and reclaiming of memory. GC (Garbage collector) makes a trip to the heap and collects all objects that are no longer used by the application and then makes them free from memory.

Memory Facts

https://www.codeproject.com/KB/cs/1095402/mem1.jpg

When any process gets triggered, separate virtual space is assigned to that process, from a physical memory which is the same and used by every process of a system, any program deals with virtual space not with physical memory, GC also deals with the same virtual memory to allocate and de-allocate memory. Basically, there are free-blocks that exist in virtual memory (also known as holes), when any object request for memory allocation manager searches for free-block and assigns memory to the said object.

Virtual memory has three blocks:

  • Free (empty space)
  • Reserved (already allocated)
  • Committed (This block is give-out to physical memory and not available for space allocation)

**You may face out of memory error due to virtual memory full.

How GC Works?

https://www.codeproject.com/KB/cs/1095402/Garbage.png

GC works on managed heap, which is nothing but a block of memory to store objects, when garbage collection process is put in motion, it checks for dead objects and the objects which are no longer used, then it compacts the space of live object and tries to free more memory.

Basically, heap is managed by different ‘Generations‘, it stores and handles long-lived and short-lived objects, see the below generations of Heap:

  • 0 Generation (Zero): This generation holds short-lived objects, e.g., Temporary objects. GC initiates garbage collection process frequently in this generation.
  • 1 Generation (One): This generation is the buffer between short-lived and long-lived objects.
  • 2 Generation (Two): This generation holds long-lived objects like a static and global variable, that needs to be persisted for a certain amount of time. Objects which are not collected in generation Zero, are then moved to generation 1, such objects are known as survivors, similarly objects which are not collected in generation One, are then moved to generation 2 and from there onwards objects remain in the same generation.

How GC Decides If Objects Are Live?

GC checks the below information to check if the object is live:

  • It collects all handles of an object that are allocated by user code or by CLR
  • Keeps track of static objects, as they are referenced to some other objects
  • Use stack provided by stack walker and JIT

When GC Gets Triggered?

There are no specific timings for GC to get triggered, GC automatically starts operation on the following conditions:

  1. When virtual memory is running out of space.
  2. When allocated memory is suppressed acceptable threshold (when GC found if the survival rate (living objects) is high, then it increases the threshold allocation).
  3. When we call GC.Collect() method explicitly, as GC runs continuously, we actually do not need to call this method.

What is Managed and Unmanaged Objects/Resources?

https://www.codeproject.com/KB/cs/1095402/managed.png VS https://www.codeproject.com/KB/cs/1095402/stack.png

In simple terms:

Managed objects are created, managed and under scope of CLR, pure .NET code managed by runtime, Anything that lies within .NET scope and under .NET framework classes such as string, int, bool variables are referred to as managed code.

UnManaged objects are created outside the control of .NET libraries and are not managed by CLR, example of such unmanaged code is COM objects, file streams, connection objects, Interop objects. (Basically, third party libraries that are referred in .NET code.)

Clean Up Unmanaged Resources

https://www.codeproject.com/KB/cs/1095402/Broom.jpg

When we create unmanaged objects, GC is unable to clear them and we need to release such objects explicitly when we finished using them. Mostly unmanaged objects are wrapped/hide around operating system resources like file streams, database connections, network related instances, handles to different classes, registries, pointers etc. GC is responsible to track the life time of all managed and unmanaged objects but still GC is not aware of releasing unmanaged resources

There are different ways to cleanup unmanaged resources:

  • Implement IDisposable interface and Dispose method
  • ‘using’ block is also used to clean unmanaged resources

***

Visits: 171
  • Home
  • About Me
  • You Tube
  • LinkedIn