Skip to Content
All posts

Essential Collections in C#

5 min read ·  — #csharp-interview#junior

Essential Collections in C#

When programming in C#, one often needs to work with a group of objects. This is where collections come in. Collections in C# are simply classes designed to hold, manage, and manipulate groups of objects. They provide different ways to organize data for efficient access and manipulation. There are two broad types of collections in C#: generic and non-generic. Generic collections are type-safe at compile time and provide better performance than their non-generic counterparts.

Common types of collections include arrays, lists, dictionaries, sets, queues, and stacks, each with their specific use cases:

  • Arrays are useful when you have a fixed number of elements, and you need to access them by their indices.
  • Lists are flexible arrays; they are best when you have an unknown number of elements to store, and you need to perform various operations like adding or removing items.
  • Dictionaries are great when you need to associate keys with values and retrieve values quickly based on their keys.
  • Sets, specifically HashSets, are beneficial when you need to ensure that all elements are unique and need to check whether an element is in the collection quickly.
  • Queues and Stacks are used when you need special kinds of insertion and retrieval orders (FIFO for queues and LIFO for stacks).

Understanding when and how to use these different types of collections is a critical skill for any C# developer, and it will greatly impact the efficiency and effectiveness of your code. The choice of a proper collection type depends on the specific requirements of your application.

Arrays

An array is a basic data structure in C#. It can be used to store multiple values of the same type in a single variable. Here's an example of creating and using an array:


int[] myArray = new int[5] {1, 2, 3, 4, 5};

for(int i=0; i<myArray.Length; i++)
{
    Console.WriteLine(myArray[i]);
}

In this example, an integer array is created and initialized with values from 1 to 5. A for loop is then used to iterate over each element and print it to the console. Arrays are zero-indexed, meaning the first element is at index 0.

Understanding generic versus non-generic collections

A generic collection in C# is strongly typed. That means the data type of the elements is known at compile time. This is in contrast to non-generic collections which can store any type of object, and type information is not known until runtime. Let's compare a generic List with a non-generic ArrayList:


List<int> myList = new List<int>() {1, 2, 3, 4, 5};

ArrayList myArrayList = new ArrayList() {1, "two", 3, "four", 5};

In the first line, myList can only hold integers, because it's a generic collection of type int. The second line myArrayList can hold any type of object. Using generic collections usually leads to safer and more efficient code.

Lists

List is a type of collection that is used when the number of elements is unknown. Here's an example of how to use it:


List<string> myNames = new List<string>();

myNames.Add("Alice");
myNames.Add("Bob");
myNames.Add("Charlie");

foreach(string name in myNames)
{
    Console.WriteLine(name);
}

Here, we are initializing a List of strings, and then adding names to it. We can easily iterate through it using a foreach loop.

Dictionaries

A Dictionary is a type of collection that stores data in key-value pairs. Here's an example:


Dictionary<int, string> myDictionary = new Dictionary<int, string>();

myDictionary.Add(1, "Alice");
myDictionary.Add(2, "Bob");
myDictionary.Add(3, "Charlie");

foreach(KeyValuePair<int, string> item in myDictionary)
{
    Console.WriteLine("Key: {0}, Value: {1}", item.Key, item.Value);
}

In this case, we are initializing a Dictionary with integer keys and string values. We can then add entries and iterate through them. Dictionary lookup operations are typically very fast.

Sets

Sets are used when you want a collection of unique elements. In C#, the HashSet class provides this functionality. Let's see an example:


HashSet<int> mySet = new HashSet<int>();

mySet.Add(1);
mySet.Add(2);
mySet.Add(3);
mySet.Add(2);  //This will not be added as 2 is already present in the set.

foreach(int i in mySet)
{
    Console.WriteLine(i);
}

Queues and Stacks

Queues and Stacks are data structures that differ mainly by their element access strategies - Queue follows the FIFO (First-In-First-Out) model, and Stack follows the LIFO (Last-In-First-Out) model.

Here's how to use a Queue:


Queue<string> myQueue = new Queue<string>();

myQueue.Enqueue("Alice");
myQueue.Enqueue("Bob");
myQueue.Enqueue("Charlie");

while(myQueue.Count > 0)
{
    string name = myQueue.Dequeue();
    Console.WriteLine(name);
}

And a Stack:


Stack<string> myStack = new Stack<string>();

myStack.Push("Alice");
myStack.Push("Bob");
myStack.Push("Charlie");

while(myStack.Count > 0)
{
    string name = myStack.Pop();
    Console.WriteLine(name);
}

Choosing the proper collection type

Choosing the right type of collection depends on what kind of operation you are performing:

  • If you need a collection of unique items, use a Set (HashSet).
  • If you want to access items by index, use an Array or List.
  • If you want to map keys to values, use a Dictionary.
  • If you need a first-in-first-out order, use a Queue.
  • If you need a last-in-first-out order, use a Stack.

Remember, the proper collection type can greatly increase the efficiency of your code. For example, if you need to frequently check if a collection contains a particular element, a HashSet or Dictionary would be a better choice than a List or Array, because the former two have faster lookup times.

References