Minimus Heximus
Minimus Heximus

Reputation: 2815

Does just declaring a variable of a simple type allocates memory?

I read this question in C, and I have the same question in C#.

Is it correct to say that by the code

int a;

four unassigned bytes is reserved for a before it is initialized? Or initialization is where the bytes are allocated for the first time?

Upvotes: 4

Views: 2822

Answers (4)

Chris Shain
Chris Shain

Reputation: 51349

An int declaration without assignment will (as mentioned in the comments) will be optimized away by the compiler- it will not show up at all in the program.

Assuming you are in a function (as opposed to a type definition) and assign the int, the allocation will take place from stack space when the function begins (that is, the int is allocated from memory already dedicated to that thread, and will not result in a OS allocation).

On the other hand, if the int is part of a type definition (and is used) then it will increase the allocated space of each instance of that type, wherever that type ends up being allocated (heap for classes, heap or stack for structs depending on usage).

In no situation will it result in a pointer or reference for the int itself.

Some further explanation:

Th original question refers to an int by example. An int is a fixed-length (4-byte) data structure, so the compiler notes that the method containing the declaration in question will be needing 4 bytes to store it. Rather than allocating those 4 bytes on the heap (where it puts reference types) and incurring garbage collection overhead, the compiler will reserve 4 bytes in the area of memory reserved for the current thread's method local variables (the call stack). That memory had been allocated from the OS when the thread started and it is reserved for that thread alone. If the thread runs out of that space, it's called a stack overflow.

It's worth noting here that .NET really has 2 compilers- the C# compiler that converts C# code into IL, and the JIT compiler that converts IL into machine instructions at runtime. In my answer when I say "the compiler", I am doing some hand-waving about which compiler I mean exactly, but the result is the same.

As per the comments, if I do this...

void Foo() {
  {
    int a = 5;
    Console.WriteLine(a);
  }
  {
    int a = 7;
    Console.WriteLine(a);
  }
}

... then it is possible that the compiler could re-use the stack space allocated for the first variable a for the second, as they are semantically different. But that's an optimization.

It's also worth noting that the call stack includes other information besides method-local variables- it includes the parameters to the method, space for the return value (a pointer if the function returns a reference type), and the return address as well.

Finally, I'd add that in C# your methods may be inlined by the JIT compiler- this means that the code of a called method may be copied wholesale into the body of the caller to avoid the overhead of a method call. In that case, the stack frame will include space for the called method's local variables as well.

Upvotes: 5

Mohammad Chamanpara
Mohammad Chamanpara

Reputation: 2159

Well, It depends on the variable type.
Since int is a ValueType it allocates all 4 bytes needed. There are two main categories of variables in c# : Reference Types and Value Types.In case of value Types such as int all the memory needed for the variable allocates but when you declare a variable of a reference type before using new operator it just allocates a pointer and after creating the main object it allocates the space needed for storing the variable.

Class MyType
{
...
}

MyType s; // Just a pointer
s=new MyType(); //Now allocating happens.

For more information on Reference Types see MSDN Reference Types.
For more information on Value Types see MSDN Value Types.

MSDN :

There are two kinds of types in C#: reference types and value types. Variables of reference types store references to their data (objects), while variables of value types directly contain their data. With reference types, two variables can reference the same object; therefore, operations on one variable can affect the object referenced by the other variable. With value types, each variable has its own copy of the data, and it is not possible for operations on one variable to affect the other (except in the case of ref and out parameter variables, see ref (C# Reference) and out parameter modifier (C# Reference)).

Upvotes: 2

Amira.NET
Amira.NET

Reputation: 11

A simple declaration of a variable like in your example will contain a reference, until you create an object with new keyword.

Upvotes: -3

Stuart
Stuart

Reputation: 764

An int in C# is always 4 bytes (no matter what the value).

Remember that

int a;

is the same as

int a = 0;

When declaring an int, it is given the default value of 0.

Upvotes: 2

Related Questions