STACK AND HEAP
In value and reference types in C Sharp when a C# program runs the runtime environment creates two distinct areas of memory, the stack and the heap. Let’s start talking about the stack by helping with the program below and the schematization in the figure.
THE PROGRAM TO ANALYZE THE STACK
namespace StackAndHeap; internal class Program { private static void Main() { var x1 = 10; var result = FirstMethod(x1); } private static int FirstMethod(int a) { var y = 20; int z; z = SecondMethod(y); return z + a; } private static int SecondMethod(int b) { var k = 30; return b + k; } }
The stack (stack in Italian) is a very fast area of memory, a LIFO(Last In First Out) type structure, that is, the last value stored is the first to exit. The stack in addition to the program counter keeps track of the program execution flow. But let’s go in order, we have seen in previous posts that in a console application the Main method is the first to be executed. When the program enters this method in the stack a so-called frame is created that stores all the parameters of the method (for simplicity I omitted the argument of the Main method, i.e., the array of strings) i.e., the local variables x and result in Figure 3.
THE CALL TO THE METHODS
When the call to FirstMethod arrives, program execution jumps to this method. A new frame is created on the stack in which the input parameter a and the two local variables y and z are stored. The new created frame occupies the top of the stack Figure 2.
When SecondMethod is called a frame is created again that stores all parameters and variables of SecondMethod Figure 3 and execution continues with the execution of the latter. When SecondMethod is finished, it goes back up the top of the stack specifically all the parameters and variables of this method are cleared from memory and it goes back to executing FirstMethod and so on until the last instruction of the Main method that terminates the program (Figure 4) .
L’ HEAP
The Heap (pile stack in Italian) unlike the stack is an area of memory where program execution is not tracked, this is the job of the stack but it is a cluttered area of memory where objects are stored for a time. It is the job of the Garbage Collector when there are no more references to an object to free up memory, but we will see this more in discussing Value Types and Reference Types.
VALUE TYPES AND REFERENCE TYPES
In C# all types both those we have seen so far and those we will see later such as classes, structs, and enumerations are divided into two large blocks: Types that are handled by value, such as the primitive types already seen, and reference types such as strings.
Suppose to understand the difference between the two types that in the Main method we have declared two variables:
int x = 234;
string s = “pippo“
Let us see with a figure how the runtime environment handles the int type (Value Types) and the string type (Reference Types).
Regarding the behavior of value types such as an int we see that in the stack in addition to the variable x the value 234 is stored directly i.e. the variable x contains or rather points directly to the value 234. On the other hand with regard to strings that we have already met, in the stack the variable and the reference to the string is stored i.e. in the reference is the memory location that is in the heap and contains the value “pippo”. This is the big difference between a value types that directly store the value along with the variable in the stack and reference types that in the stack or rather in the frame created by the runtime store a variable that points the reference to the object stored on the Heap.
SEMANTICS OF VALUE TYPES
Suppose our program executes the Main method in which we have declared two variables x and y of type integer and assign the value of x to y. The runtime as you know creates a frame in the stack and within the frame stores the variables x and y along with their values.
int x = 120;
int y = 50;
y=x;
x=5;
let us see with a figure the situation that is created in the stack.
When the program flow in Main assigns the value of x to y two separate copies are created for the literal 120 value one for x and the other for y. When we reassign the value to x (x=5) we see that y retains the previous value and x assumes 5. This stands to show that for value types the two variables are completely unrelated.
SEMANTICS OF REFERENCE TYPES
Suppose that in our Main method we declare an array of int, arrays we will see later. An array is a collection of objects of a certain type the syntax for declaring an array is given further down. Then suppose we create a second array y and assign it to x; Finally we modify the first element of x. Let us see with a figure what the situation looks like in memory.
int [] x = new [] {30,40};
int [] y = x;
x[0] = 10;
PASSING PARAMETERS BY VALUE
PASSING PARAMETERS BY REFERENCE
THE NULL KEYWORD
The keyword null removes the reference from the stack that contained the memory location of the object pointed to on the heap.
If the object remains orphaned on the heap, that is, it no longer has any active references there is a mechanism in C# called a garbage collector that scans and cleans up all the objects left orphaned on the heap. If there was not this mechanism which is automatic soon it would result in a memory leak. Let us clarify the concept with a picture.
FURTHER INFORMATION
In C#, value types and reference types are two fundamental categories that determine the behavior of variables and memory management.
Let’s look at the main differences and examples of each type.
TYPES OF VALUE
Value types contain their data directly.
When a value type variable is allocated to another variable, a copy of the data is created.
Value types are allocated in the stack, which generally provides faster access but a lifetime limited to the execution context.
EXAMPLES OF VALUE TYPES
– Primitive Types: int, char, float, double, bool
-Structures: struct
-Enumerations: enum
CHARACTERISTICS OF VALUE TYPES
–Located in the stack
-Contain data directly
-Copy of data during assignment
-Cannot be null (unless declared as nullable with ?)
Example
int a = 10;
int b = a; // b is a copy of a, so b = 10
b = 20; // Changing b does not change a
Console.WriteLine(a); // Output: 10
Console.WriteLine(b); // Output: 20
TYPES OF REFERENCE
Reference types contain a reference to data. When a variable of a reference type is assigned to another variable, both variables refer to the same data. Reference types are allocated in the heap, which can lead to more complex memory management but provides an extended lifetime until there is no longer any reference to the data.
EXAMPLES OF REFERENCE TYPES
–Classes: class
-Interfaces: interface
-Delegates: delegates
-Strings: string
-Array
CHARACTERISTICS OF REFERENCE TYPES
–Located in the heap
-Contains a reference to the data
-Data sharing during assignment
-May be null and void
Example
class Person
{
public string Name { get; set; }
}
Person person1 = new Person { Name =“Alice” };
Person person2 = person1; // person2 refers to the same data as person1
person2.Name =“Bob“; // Changing person2 also changes person1
Console.WriteLine(person1.Name); // Output: Bob
Console.WriteLine(person2.Name); // Output: Bob
Use value types for small, immutable data that have a short life cycle.
Use reference types for complex objects and data that require a longer life cycle and more complex manipulations.
These concepts are fundamental to understanding memory management, efficiency, and behavior of C# applications.
Leave A Comment