C# Linq has an extentions SingleOrDefault and FirstOrDefault, which returns first item from list, so in this article, I have mentioned SingleOrDefault vs FirstOrDefault in C# using Console application, so you can understand the difference between both of them.
Here is the basic defination of SingleOrDefault and FirstOrDefault
SingleOrDefault
: Returns the only element of a sequence, or a default value if the sequence is empty, but this method throws an exception if there is more than one element in the sequence.FirstOrDefault
: Returns the first element of the sequence that satisfies a condition, or a specified default value if no such element is found.
Consider we have below C# code:
using System;
using System.Collections.Generic;
using System.Linq;
namespace SingleOrDefaultVSFirstOrDefault
{
public class Program
{
static void Main(string[] args)
{
var students = new List<Student>()
{
new Student{Id = 1, FullName = "John Wick"},
new Student{Id = 2, FullName = "Alice Dean"},
new Student{Id = 3, FullName = "John Wick"}
};
//works fine
var data = students.FirstOrDefault(a => a.FullName == "John Wick");
Console.WriteLine("FirstOrDefault returns student with ID: " + data.Id);
Console.WriteLine();
//this will throw error, since there are multiple items to return from
var data1 = students.SingleOrDefault(a => a.FullName == "John Wick");
}
public class Student
{
public int Id { get; set; }
public string FullName { get; set; }
}
}
}
Then output of the above code would be as below
FirstOrDefault returns student with ID: 1
Unhandled exception. System.InvalidOperationException: Sequence contains more than one matching element
at System.Linq.ThrowHelper.ThrowMoreThanOneMatchException()
at System.Linq.Enumerable.SingleOrDefault[TSource](IEnumerable`1 source, Func`2 predicate)
at SingleOrDefaultVSFirstOrDefault.Program.Main(String[] args) in C:\Users\vks-ssd\source\repos\CharToAscii\CharToAscii\Program.cs:line 23
Reason for the above exception is that
SingleOrDefault
throws an exception, If your result set returns many records.
So we conclude that:
If your result set returns 0 records:
SingleOrDefault returns the default value for the type (example, default value for int is 0) while FirstOrDefault returns the default value for the type
If you result set returns 1 record:
SingleOrDefault returns that record while FirstOrDefault returns that record
If your result set returns many records:
SingleOrDefault throws an exception while FirstOrDefault returns the first record
Performance Difference
FirstOrDefault
is usually faster, it iterates until it finds the element and only has to iterate the whole enumerable when it doesn't find it. while SingleOrDefault
needs to check if there is only one element and therefore always iterates the whole enumerable.
To be precise, SingleOrDefault
iterates until it finds a second element and throws an exception. But in most cases, there is no second element.
So you can use SingleOrDefault
only when you don't care about performance and what to check if there is only 1 item in the list and throw exception if not.
Generally, in practice, we are more likely to use FirstOrDefault
since it is better performance wise and we usually don't want to get error details if there are more than 1 same items in list.
You may also like to read:
Remove last character from string in C#
What is Console.Log Equivalent in C#?
Fibonacci series In C# (Various possible ways)
Foreach() vs Parallel.Foreach() in C#