10 LINQ C# Interview Questions and Answers
Prepare for your C# interview with this guide on LINQ. Enhance your understanding and showcase your skills with common and advanced questions.
Prepare for your C# interview with this guide on LINQ. Enhance your understanding and showcase your skills with common and advanced questions.
Language Integrated Query (LINQ) in C# is a powerful feature that allows developers to write queries directly within their code, providing a more readable and concise way to handle data manipulation. LINQ bridges the gap between the world of objects and the world of data, enabling developers to work with data from different sources such as databases, XML documents, and in-memory collections using a consistent syntax.
This article offers a curated selection of LINQ-related questions and answers to help you prepare for your upcoming interview. By familiarizing yourself with these questions, you will gain a deeper understanding of LINQ’s capabilities and be better equipped to demonstrate your proficiency in C# during technical discussions.
LINQ (Language Integrated Query) in C# allows developers to write queries directly within the C# language, providing a consistent and readable way to query various data sources. It offers several benefits:
Example:
using System; using System.Collections.Generic; using System.Linq; class Program { static void Main() { List<int> numbers = new List<int> { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 }; var evenNumbers = from num in numbers where num % 2 == 0 select num; foreach (var num in evenNumbers) { Console.WriteLine(num); } } }
Deferred execution means that the query is not executed at the point of its declaration but when iterated over, allowing for query composition and optimization. Immediate execution occurs when methods like ToList()
, ToArray()
, and Count()
are used, as they require the result set to be generated immediately.
Example:
// Deferred Execution var numbers = new List<int> { 1, 2, 3, 4, 5 }; var query = numbers.Where(n => n > 2); // The query is not executed here foreach (var number in query) { Console.WriteLine(number); // The query is executed here } // Immediate Execution var immediateQuery = numbers.Where(n => n > 2).ToList(); // The query is executed here foreach (var number in immediateQuery) { Console.WriteLine(number); }
To find the maximum value in a collection of objects based on a specific property, use LINQ’s Max
method.
Example:
using System; using System.Collections.Generic; using System.Linq; public class Product { public string Name { get; set; } public decimal Price { get; set; } } public class Program { public static void Main() { List<Product> products = new List<Product> { new Product { Name = "Product1", Price = 10.0m }, new Product { Name = "Product2", Price = 20.0m }, new Product { Name = "Product3", Price = 15.0m } }; decimal maxPrice = products.Max(p => p.Price); Console.WriteLine("The maximum price is: " + maxPrice); } }
Join
method and how is it used?The Join
method in LINQ combines elements from two sequences based on a common key, similar to the SQL JOIN operation.
Example:
using System; using System.Collections.Generic; using System.Linq; public class Program { public static void Main() { List<Customer> customers = new List<Customer> { new Customer { CustomerId = 1, Name = "John" }, new Customer { CustomerId = 2, Name = "Jane" } }; List<Order> orders = new List<Order> { new Order { OrderId = 1, CustomerId = 1, Product = "Laptop" }, new Order { OrderId = 2, CustomerId = 2, Product = "Tablet" } }; var query = from customer in customers join order in orders on customer.CustomerId equals order.CustomerId select new { customer.Name, order.Product }; foreach (var item in query) { Console.WriteLine($"{item.Name} ordered {item.Product}"); } } } public class Customer { public int CustomerId { get; set; } public string Name { get; set; } } public class Order { public int OrderId { get; set; } public int CustomerId { get; set; } public string Product { get; set; } }
To order a list of objects by multiple properties, use the OrderBy
and ThenBy
methods.
Example:
using System; using System.Collections.Generic; using System.Linq; public class Person { public string FirstName { get; set; } public string LastName { get; set; } public int Age { get; set; } } public class Program { public static void Main() { List<Person> people = new List<Person> { new Person { FirstName = "John", LastName = "Doe", Age = 30 }, new Person { FirstName = "Jane", LastName = "Smith", Age = 25 }, new Person { FirstName = "John", LastName = "Smith", Age = 20 }, new Person { FirstName = "Jane", LastName = "Doe", Age = 35 } }; var sortedPeople = people .OrderBy(p => p.FirstName) .ThenBy(p => p.LastName) .ThenBy(p => p.Age); foreach (var person in sortedPeople) { Console.WriteLine($"{person.FirstName} {person.LastName}, Age: {person.Age}"); } } }
To select distinct elements from a collection, use the Distinct
method.
Example:
using System; using System.Collections.Generic; using System.Linq; class Program { static void Main() { List<int> numbers = new List<int> { 1, 2, 2, 3, 4, 4, 5 }; IEnumerable<int> distinctNumbers = numbers.Distinct(); foreach (int number in distinctNumbers) { Console.WriteLine(number); } } }
Flatten a list of lists using the SelectMany
method.
Example:
using System; using System.Collections.Generic; using System.Linq; public class Program { public static void Main() { List<List<int>> listOfLists = new List<List<int>> { new List<int> { 1, 2, 3 }, new List<int> { 4, 5, 6 }, new List<int> { 7, 8, 9 } }; List<int> flattenedList = listOfLists.SelectMany(x => x).ToList(); foreach (var item in flattenedList) { Console.WriteLine(item); } } }
A left outer join returns all elements from the first collection, along with matching elements from the second collection. If there is no match, the result will contain null for the elements from the second collection.
Example:
using System; using System.Collections.Generic; using System.Linq; public class Program { public class Person { public int Id { get; set; } public string Name { get; set; } } public class Order { public int OrderId { get; set; } public int PersonId { get; set; } public string Product { get; set; } } public static void Main() { List<Person> people = new List<Person> { new Person { Id = 1, Name = "John" }, new Person { Id = 2, Name = "Jane" }, new Person { Id = 3, Name = "Jake" } }; List<Order> orders = new List<Order> { new Order { OrderId = 1, PersonId = 1, Product = "Laptop" }, new Order { OrderId = 2, PersonId = 2, Product = "Tablet" } }; var query = from person in people join order in orders on person.Id equals order.PersonId into personOrders from order in personOrders.DefaultIfEmpty() select new { PersonName = person.Name, Product = order?.Product ?? "No Orders" }; foreach (var result in query) { Console.WriteLine($"{result.PersonName}: {result.Product}"); } } }
LINQ can sometimes lead to performance issues due to deferred execution, multiple enumerations, and the creation of intermediate collections. To optimize LINQ queries, consider the following strategies:
Any
and All
over Count
when checking for the existence of elements.ToList
or ToArray
judiciously.Example:
var numbers = Enumerable.Range(1, 1000000).ToList(); // Inefficient: Multiple enumerations var evenNumbersCount = numbers.Where(n => n % 2 == 0).Count(); var evenNumbersSum = numbers.Where(n => n % 2 == 0).Sum(); // Optimized: Single enumeration var evenNumbers = numbers.Where(n => n % 2 == 0).ToList(); var optimizedEvenNumbersCount = evenNumbers.Count; var optimizedEvenNumbersSum = evenNumbers.Sum();
Select
and SelectMany
.Select
and SelectMany
are both projection operators in LINQ.
Select
: Projects each element of a collection into a new form based on the provided selector function.SelectMany
: Projects each element of a collection into an IEnumerable and flattens the resulting collections into a single collection.Example:
List<int> numbers = new List<int> { 1, 2, 3, 4, 5 }; // Using Select var selectResult = numbers.Select(n => n * 2); // Output: { 2, 4, 6, 8, 10 } // Using SelectMany List<List<int>> numberGroups = new List<List<int>> { new List<int> { 1, 2, 3 }, new List<int> { 4, 5, 6 }, new List<int> { 7, 8, 9 } }; var selectManyResult = numberGroups.SelectMany(group => group); // Output: { 1, 2, 3, 4, 5, 6, 7, 8, 9 }