Differences between IEnumerable and IQueryable in C#

When working with in-memory collections—where data is kept locally in the memory of the application—select IEnumerable<T>. When working with huge data sets or querying external data sources, use IQueryable<T> as it enables effective server-side processing and query optimization.

In every .NET application we need to manipulate IEnumerable and IQueryable interfaces to hold collections. The basic use of IEnumerable and IQueryable is to hold the collection of data & perform Ordering, Grouping & Filtering of data based on project/application requirements. The first thing to keep in mind is that since the IQueryable interface is an inheritance of IEnumerable, it possesses all of IEnumerable's capabilities. Both are limited to process on C# collections. The important difference between IEnumerableand IQueryable is: IQueryable - The Filter is apply at server level/side and fetch only required results from source. So processing time is less. IEnumerable- It fetch all data from source first and later apply the filter at client level/side. Which can be result in fetching unnecessary data and it increase processing time. Lets understand this with an example. We have created Console application in .NET Core to fetch Books from SQL Server database and we are using Entity Framework Core to fetch the books (books table). We built it over Code-First approach. This is our Book.cs Entity
[Table("Books")]
public class Book
{
    [Key]
    public int BookId { get; set; }

    [StringLength(255)]
    public string? Title { get; set; }
    public decimal Price { get; set; }
}
We have around 10 records added into database by using seed data method. Lets understand the differences by using below  code. We have written both queries in LINQ.
class Program
{
    static void Main(string[] args)
    {
        using (var context = new BookDemoDbContext())
        {

            var booksIEnumerable = (from book in context.Books
                                    select book)
                                    .AsEnumerable<Book>().Take(2).ToList();


            var booksIQurable = (from book in context.Books
                                 select book)
                                 .AsQueryable<Book>().Take(2).ToList();
        }

        Console.ReadKey();
    }
}
In first query we are trying to fetch 2 books in IEnumerable interface.
var booksIEnumerable = (from book in context.Books
                        select book)
                        .AsEnumerable<Book>().Take(2).ToList();
Lets see what above LINQ query has been executed in SQL Server with the help of SQL Server profiler (for IEnumerable). IEnumerable - Profiler Below query is traced in profiler. The query is simple SELECT statement without any where clause or TOP statement. It means it selecting all rows from SQL server database and just pick 2 records on client side.
SELECT [b].[BookId], [b].[Price], [b].[Title]
FROM [Books] AS [b]
The diagram shows graphical representation of how  IEnumerableworks. IEnumerable working In first query we are trying to fetch 2 books in IQueryableinterface.
var booksIQurable = (from book in context.Books
                     select book)
                     .AsQueryable<Book>().Take(2).ToList();
Lets see what above LINQ query has been executed in SQL Server with the help of SQL Server profiler (for IQueryable). IQueryable - Profiler Below query is traced in profiler. The TOP filter has been applied with parameter and its value = 2, so it means it fetch only 2 records from Books table. So it avoids fetching unnecessary data from database.
exec sp_executesql N'SELECT TOP(@__p_0) [b].[BookId], [b].[Price], [b].[Title]
FROM [Books] AS [b]',N'@__p_0 int',@__p_0=2
The diagram shows graphical representation of how  IQueryable works. IQueryable Interface  

Download Source Code

https://github.com/mayurlohite/IEnumerableVsIQueryable

See the difference in action, watch this video

Conclusion

Hence, when working with in-memory collections—where data is kept locally in the memory of the application—select IEnumerable<T>. When working with huge data sets or querying external data sources, use IQueryable<T> as it enables effective server-side processing and query optimization. Your performance needs and the type of data source will determine which option is best. If you have any questions, Please connect me on LinkedIn. Explore more articles.

If you find anything inappropriate please report it here.

Leave a Reply

Please login to post comments.

Top