C# tutorials > Core C# Fundamentals > Basics and Syntax > What is boxing and unboxing?
What is boxing and unboxing?
int
, bool
, struct
) and reference types (like object
). They enable value types to be treated as objects and vice versa, which is crucial for the C# type system and certain operations, especially when dealing with collections or methods expecting objects.
Boxing: Converting Value Types to Object Types
object
reference. In essence, it involves allocating memory on the heap for a new object and copying the value type's data into that object. The object
variable then holds a reference to this newly created boxed value. In the example, the integer variable i
, which is a value type, is boxed into an object referred to by obj
. The original value type remains unchanged.
int i = 123;
object obj = i; // Boxing
Console.WriteLine(obj); // Output: 123
Unboxing: Converting Object Types to Value Types
obj
, which contains a boxed integer, is unboxed back into an integer variable i
. An InvalidCastException
will be thrown if the object does not contain a value type that can be converted to the specified type.
object obj = 123; // Boxing
int i = (int)obj; // Unboxing
Console.WriteLine(i); // Output: 123
Concepts Behind the Snippet
Real-Life Use Case Section
ArrayList
. ArrayList
stores elements as objects. Therefore, when adding value types (like int
, bool
) to an ArrayList
, they are implicitly boxed. When retrieving them, they need to be explicitly unboxed. However, the use of non-generic collections is generally discouraged in modern C# due to type safety issues and performance overhead associated with boxing and unboxing. Generic collections (e.g., List
) provide better type safety and avoid boxing/unboxing when dealing with value types.
using System.Collections;
ArrayList list = new ArrayList();
list.Add(10);
list.Add("Hello");
list.Add(true);
int number = (int)list[0]; // Unboxing
string message = (string)list[1]; //Unboxing
bool flag = (bool)list[2]; //Unboxing
Console.WriteLine($"Number: {number}, Message: {message}, Flag: {flag}");
Best Practices
List
instead of ArrayList
) to avoid boxing when working with value types.is
or as
operators to perform type checking before unboxing.
Interview Tip
When to Use Them
In modern C#, however, prefer generics to avoid boxing and unboxing wherever possible.object
parameters.
Memory Footprint
Alternatives
List
instead of ArrayList
for a list of integers.
Pros
Cons
InvalidCastException
if the types are incompatible.
FAQ
-
What happens if I try to unbox an object to the wrong type?
If you attempt to unbox an object to a type that it doesn't actually contain, aSystem.InvalidCastException
will be thrown at runtime. For example, if you try to unbox an object containing a boxedint
to astring
, an exception will occur. -
Does boxing modify the original value type variable?
No, boxing creates a new object on the heap. The original value type variable remains unchanged. Boxing copies the value of the value type into the new object. -
Why are generics preferred over boxing/unboxing in modern C#?
Generics provide type safety at compile time, avoiding the runtime exceptions that can occur with unboxing. They also eliminate the performance overhead associated with boxing and unboxing because they operate directly on the specific value type without requiring conversion to and from objects.