C# Interview Questions for Developers

Use our engineer-created questions to interview and hire the most qualified C# developers for your organization.

C#

Known primarily for its use in a variety of Microsoft platforms and products, C# is also popular because of its gentle learning curve, strong developer community, and utilization by the Unity game engine.

According to the CoderPad 2023 Developer survey, C# is the 4th most in-demand language among technical recruiters and hiring managers.

We have created practical coding exercises and interview questions below to assess developers’ C# proficiency during coding interviews.

Furthermore, we have established a list of top practices to guarantee that your interview questions precisely measure the candidates’ C# expertise.

C# example question

Help us design a parking lot

Hey candidate! Welcome to your interview. Boilerplate is provided. Feel free to change the code as you see fit. To run the code at any time, please hit the run button located in the top left corner.

Goals: Design a parking lot using object-oriented principles

Here are a few methods that you should be able to run:

  • Tell us how many spots are remaining
  • Tell us how many total spots are in the parking lot
  • Tell us when the parking lot is full
  • Tell us when the parking lot is empty
  • Tell us when certain spots are full e.g. when all motorcycle spots are taken
  • Tell us how many spots vans are taking up

Assumptions:

  • The parking lot can hold motorcycles, cars and vans
  • The parking lot has motorcycle spots, car spots and large spots
  • A motorcycle can park in any spot
  • A car can park in a single compact spot, or a regular spot
  • A van can park, but it will take up 3 regular spots
  • These are just a few assumptions. Feel free to ask your interviewer about more assumptions as needed

Junior C# interview questions

Question: What is the difference between a value type and a reference type in C#? Can you provide an example of each?
Answer: Value types store their value directly in memory, while reference types store a reference to the object in memory. An example of a value type is an integer (int), while an example of a reference type is a string.

Question: What is the purpose of the using statement in C#? Can you provide an example?
Answer: The using statement is used to ensure that an object is disposed of properly, even if an exception is thrown. An example would be using a FileStream object to read from a file:

using (FileStream fileStream = new FileStream("file.txt", FileMode.Open))
{
    // Code to read from file here
}Code language: C# (cs)

Question: You are given the following code. Can you identify and fix the issue?

int x = 5;
int y = 2;
int result = x / y;Code language: C# (cs)

Answer: The issue is that the division operator is used with two integers, which will result in integer division. To fix this, one of the operands should be cast to a double or float:

int x = 5;
int y = 2;
double result = (double)x / y;Code language: C# (cs)

Question: What is a constructor in C#? How is it used?
Answer:
A constructor is a special method that is used to initialize an object when it is created. It is called automatically when an object is instantiated using the new keyword. An example of a constructor is:

public class MyClass
{
    public int x;

    public MyClass()
    {
        x = 5;
    }
}

MyClass myObject = new MyClass();
Console.WriteLine(myObject.x); // Outputs 5Code language: C# (cs)

Question: What is the difference between a private and public access modifier in C#?
Answer:
Private members can only be accessed within the same class, while public members can be accessed from any code that has access to the class. An example of a private member is a private variable:

public class MyClass
{
    private int x = 5;

    public void PrintX()
    {
        Console.WriteLine(x); // Can only be accessed within the class
    }
}Code language: C# (cs)

Question: You are given the following code. Can you identify and fix the issue?

int[] myArray = new int[3];
myArray[3] = 5;Code language: C# (cs)

Answer: The issue is that the array index is out of bounds. Arrays in C# are zero-indexed, so the highest valid index for an array of length 3 is 2. To fix this, the array should be resized or the index should be changed:

int[] myArray = new int[4]; // Resizing the array
myArray[3] = 5;Code language: C# (cs)

or

int[] myArray = new int[3];
myArray[2] = 5; // Changing the indexCode language: C# (cs)

Question: What is the difference between an abstract class and an interface in C#?
Answer:
An abstract class is a class that cannot be instantiated and can contain both abstract and non-abstract members, while an interface is a contract that defines a set of methods and properties that a class must implement. An example of an abstract class is:

public abstract class MyAbstractClass
{
    public abstract void MyAbstractMethod();

    public void MyNonAbstractMethod()
    {
        // Code here
    }
}Code language: C# (cs)

An example of an interface is:

public interface IMyInterface
{
    void MyInterfaceMethod();
}Code language: C# (cs)

Question: You are given the following code. Can you identify and fix the issue?

public class MyClass
{
    public void MyMethod()
    {
        Console.WriteLine("My method");
    }
}

MyClass myObject = null;
myObject.MyMethod();Code language: C# (cs)

Answer: The issue is that the myObject variable is null and cannot be used to call the MyMethod method. To fix this, the myObject variable must be instantiated:

MyClass myObject = new MyClass();
myObject.MyMethod();Code language: C# (cs)

Question: What is the difference between a static and non-static member in C#?
Answer:
A static member belongs to the class itself and not to any instance of the class, while a non-static member belongs to an instance of the class. An example of a static member is a static variable:

public class MyClass
{
    public static int x = 5;

    public void MyMethod()
    {
        Console.WriteLine(x); // Accessing a static variable
    }
}Code language: C# (cs)

An example of a non-static member is a non-static method:

public class MyClass
{
    public int x = 5;

    public void MyMethod()
    {
        Console.WriteLine(x); // Accessing a non-static variable
    }
}Code language: C# (cs)

Question: What is the purpose of a try-catch block in C#? Can you provide an example?
Answer:
A try-catch block is used to handle exceptions that may occur during the execution of a block of code. The try block contains the code that may throw an exception, and the catch block contains the code that handles the exception. An example of a try-catch block is:

try
{
    int x = 5;
    int y = 0;
    int result = x / y; // This will throw a DivideByZeroException
}
catch (DivideByZeroException ex)
{
    Console.WriteLine("Cannot divide by zero");
}Code language: C# (cs)

Intermediate C# interview questions

Question: The following code snippet throws a NullReferenceException. Can you fix it and explain what caused the exception?

string name = null;
int length = name.Length;Code language: C# (cs)

Answer: The exception is thrown because name is null, and you cannot call the Length property on a null reference. To fix the code, you can check whether name is null before accessing its Length property, like this:

string name = null;
int length = name?.Length ?? 0;Code language: C# (cs)

This code uses the null-conditional operator ?. to guard against null references, and the null-coalescing operator ?? to provide a default value of 0 if name is null.

Question: What is the difference between a value type and a reference type in C#?
Answer:
A value type is a type that holds its value in its own memory space, while a reference type is a type that holds a reference to its value in a separate memory space. Value types are stored on the stack, while reference types are stored on the heap.

Question: The following code snippet throws a System.InvalidCastException. Can you fix it and explain what caused the exception?

object obj = "Hello";
int length = (int)obj;Code language: C# (cs)

Answer: The exception is thrown because you are trying to cast a string object to an integer, which is not a valid cast. To fix the code, you can use the Convert.ToInt32 method to convert the string to an integer, like this:

object obj = "Hello";
int length = Convert.ToInt32(obj);Code language: C# (cs)

This code uses the Convert.ToInt32 method to perform the conversion, which can handle various types of inputs and return a default value if the input is null or cannot be converted.

Question: What is the difference between a delegate and an event in C#?
Answer:
A delegate is a type that represents a reference to a method, while an event is a language construct that allows you to publish and subscribe to notifications of certain actions or changes in the state of an object. An event is based on a delegate type that specifies the signature of the methods that can handle the event.

Question:The following code snippet uses a foreach loop to iterate over a List. Can you suggest an alternative way to iterate over the list?

List<int> numbers = new List<int> { 1, 2, 3, 4, 5 };
foreach (int number in numbers)
{
    Console.WriteLine(number);
}Code language: C# (cs)

Answer: An alternative way to iterate over the list is to use a for loop with an index variable, like this:

List<int> numbers = new List<int> { 1, 2, 3, 4, 5 };
for (int i = 0; i < numbers.Count; i++)
{
    int number = numbers[i];
    Console.WriteLine(number);
}Code language: C# (cs)

This code uses the Count property of the list to determine the number of elements, and the indexer [] to access each element by its index.

Question: What is a lambda expression, and how is it different from an anonymous method in C#?
Answer:
A lambda expression is an anonymous function that can be used to create delegates, expression trees, or function objects. Lambda expressions are often used in LINQ queries or to define event handlers. An anonymous method is a method without a name that can be used to create delegates.

Question: The following code snippet declares a nullable integer variable and assigns it a null value. Can you suggest two ways to check whether the variable is null and retrieve its value if it is not null?

int? number = null;Code language: C# (cs)

Answer: Two ways to check whether the variable is null and retrieve its value if it is not null are:

  • Using the null-conditional operator ?. and the null-coalescing operator ??:
  int value1 = number?.Value ?? 0;

This code checks whether number is null using the null-conditional operator ?. and returns its value using the Value property if it is not null. If number is null, the null-coalescing operator ?? provides a default value of 0.

  • Using the GetValueOrDefault method:
  int value2 = number.GetValueOrDefault();

This code returns the value of number if it is not null, or the default value of 0 if it is null. The GetValueOrDefault method is a shorthand for the null-coalescing operator ?? with a default value of the type’s default value.

Question: What is a generic type in C#, and how is it different from a non-generic type?
Answer:
A generic type is a type that is parameterized by one or more type parameters, which allow the same type to be used with different types of arguments. Generic types are often used to create reusable code that can work with any type, such as collections or algorithms. Non-generic types are types that do not have any type parameters and can only work with a specific type or set of types.

Question: The following code snippet defines a class with a public property and a private field. Can you suggest a way to make the property read-only without changing its accessibility modifier?

class Person
{
    private string name;

    public string Name
    {
        get { return name; }
        set { name = value; }
    }
}Code language: C# (cs)

Answer: One way to make the property read-only without changing its accessibility modifier is to remove the setter and initialize the private field in the constructor, like this:

class Person
{
    private readonly string name;

    public Person(string name)
    {
        this.name = name;
    }

    public string Name
    {
        get { return name; }
    }
}Code language: C# (cs)

This code uses the readonly keyword to make the private field read-only, which means it can only be initialized in the constructor. The property is still publicly accessible, but the setter has been removed, which makes it read-only.

Question: What is the difference between an abstract class and an interface in C#?
Answer:
An abstract class is a class that cannot be instantiated directly and can contain abstract methods, which are methods without an implementation that must be implemented by derived classes. An abstract class can also contain non-abstract methods with an implementation, fields, properties, and events. An interface is a type that defines a set of members that must be implemented by any class that implements the interface. An interface cannot contain fields or implementations, only method signatures, properties, and events. A class can inherit from multiple interfaces, but only from one abstract class.

Senior C# interview questions

Question: Fix the following C# code:

class Program
{
    static void Main(string[] args)
    {
        List<string> fruits = new List<string>();
        fruits.Add("Apple");
        fruits.Add("Banana");
        fruits.Add("Orange");
        Console.WriteLine(fruits[3]);
    }
}Code language: C# (cs)

Answer: The code above attempts to access an index that is out of bounds in the fruits list, since the list only has three elements. To fix this, we can change the last line to Console.WriteLine(fruits[2]); to print the last element of the list.

Question: What is a monad, and how can it be used in C#?

Answer: A monad is a design pattern used in functional programming that provides a way to encapsulate a computation with a specific set of rules, such as error handling, state management, or non-determinism. In C#, monads can be implemented using the LINQ query syntax, which provides a way to compose operations on collections, such as filtering, mapping, and grouping, in a declarative and composable way.

Question: Fix the following C# code:

class Calculator
{
    public static void Main()
    {
        int result = Add(2, 3);
        Console.WriteLine(result);
    }

    public static int Add(int x, int y)
    {
        return x - y;
    }
}Code language: C# (cs)

Answer: The Add method in the code above returns the subtraction of x and y, instead of their sum. To fix this, we can change the return statement to return x + y;.

Question: Fix the following C# code:

class Program
{
    static void Main(string[] args)
    {
        int[] numbers = { 1, 2, 3 };
        Console.WriteLine(Sum(numbers));
    }

    public static int Sum(params int[] numbers)
    {
        int sum = 0;
        foreach (int number in numbers) {
            sum += numbers;
        }
        return sum;
    }
}Code language: C# (cs)

Answer: The Sum method in the code above attempts to add the numbers array to itself in the loop, instead of adding the number variable to the sum variable. To fix this, we can change the sum += numbers; statement to sum += number;.

Question: Can you explain the concept of lazy evaluation, and how it can be used in C#?

Answer: Lazy evaluation is a programming technique that defers the evaluation of an expression until it is needed, usually for performance or memory reasons. In C#, lazy evaluation can be implemented using the Lazy<T> class, which provides a way to create an object that is initialized on first use. This can be useful for delaying expensive or time-consuming operations, avoiding unnecessary calculations, and improving startup time and memory usage. Lazy evaluation can also be used in conjunction with functional programming techniques, such as currying and partial application, to create composable and reusable code.

Question: Fix the following C# code:

class Program
{
    static void Main(string[] args)
    {
        Dictionary<string, int> ages = new Dictionary<string, int>();
        ages["Alice"] = 25;
        ages["Bob"] = 30;
        ages["Charlie"] = 35;
        Console.WriteLine(ages["David"]);
    }
}Code language: C# (cs)

Answer: The code above attempts to access a key that does not exist in the ages dictionary, which results in a KeyNotFoundException. To fix this, we can either add a key-value pair for David to the dictionary, or use the TryGetValue method to check if the key exists before accessing its value, like this:

int age;
if (ages.TryGetValue("David", out age)) {
    Console.WriteLine(age);
} else {
    Console.WriteLine("David is not in the dictionary.");
}Code language: JavaScript (javascript)

Question: Can you explain what functional programming is, and what are some benefits and drawbacks of using it in C#?

Answer: Functional programming is a programming paradigm that emphasizes the use of functions to solve problems, rather than mutable state and imperative control flow. Some benefits of using functional programming in C# include better code modularity, testability, and parallelism, as well as more concise and expressive code. Some drawbacks of using functional programming in C# include a steeper learning curve, potential performance overhead, and difficulties in working with mutable data structures.

Question: Fix the following C# code:

class Program
{
    static void Main(string[] args)
    {
        string[] names = { "Alice", "Bob", "Charlie" };
        foreach (string name in names) {
            Console.WriteLine(names[0]);
        }
    }
}Code language: C# (cs)

Answer: The foreach loop in the code above always prints the first element of the names array, instead of the current element. To fix this, we can change the Console.WriteLine statement to Console.WriteLine(name);.

Question: Can you explain the SOLID principles of object-oriented design, and how they can be applied in C#?

Answer: The SOLID principles are a set of guidelines for designing object-oriented systems that are easy to maintain, extend, and reuse. They stand for:

  • Single Responsibility Principle (SRP): a class should have only one reason to change.
  • Open/Closed Principle (OCP): a class should be open for extension but closed for modification.
  • Liskov Substitution Principle (LSP): a derived class should be substitutable for its base class without changing the correctness of the program.
  • Interface Segregation Principle (ISP): a class should not be forced to depend on methods it does not use.
  • Dependency Inversion Principle (DIP): high-level modules should not depend on low-level modules, but both should depend on abstractions.

In C#, the SOLID principles can be applied using techniques such as dependency injection, inversion of control, and interfaces to decouple modules, reduce dependencies, and increase testability and flexibility.

Question: Fix the following C# code:

class Program
{
    static void Main(string[] args)
    {
        int[] numbers = { 1, 2, 3 };
        Console.WriteLine(Sum(numbers));
    }

    public static int Sum(params int[] numbers)
    {
        int sum = 0;
        foreach (int number in numbers) {
            sum += numbers;
        }
        return sum;
    }
}Code language: C# (cs)

Answer: The Sum method in the code above attempts to add the numbers array to itself in the loop, instead of adding the number variable to the sum variable. To fix this, we can change the sum += numbers; statement to sum += number;.

Question: Can you explain what the factory pattern is, and how it can be used in C#?

Answer: The factory pattern is a creational design pattern that provides an interface for creating objects, but allows subclasses to decide which class to instantiate. In C#, the factory pattern can be implemented using a factory class or method that returns an instance of a specific class based on some input parameters or conditions. This can be useful for encapsulating object creation logic, decoupling client code from concrete classes, and providing a way to switch between different implementations without changing the client code.

1,000 Companies use CoderPad to Screen and Interview Developers

Best interview practices for C# roles

To carry out successful C# interviews, it is crucial to take into account various aspects, such as the applicant’s background and the specific engineering role. To guarantee a productive interview experience, we suggest implementing the following best practices:

  • Formulate technical questions that correspond to real-life business situations within your organization. This strategy will effectively engage the applicant and aid in evaluating their suitability for your team.
  • Foster a collaborative atmosphere by encouraging the applicant to ask questions during the interview.
  • If you’re using C# for web development, also make sure to assess candidates for comprehension of ASP.NET Core and its models (MVC, Web API, AJAX, …), as well as knowledge of related web technologies like HTML, CSS and JavaScript.

Furthermore, adhering to standard interview procedures is essential when administering C# interviews. This entails adjusting the difficulty of the questions to align with the applicant’s abilities, offering timely updates on their application progress, and presenting them with the chance to inquire about the assessment process and collaboration with you and your team.