After upgrading to ReSharper5 it gives me even more useful tips on code improvements. One I see everywhere now is a tip to replace foreach-statements with LINQ queries. Take this example:
private Ninja FindNinjaById(int ninjaId)
{
foreach (var ninja in Ninjas)
{
if (ninja.Id == ninjaId)
return ninja;
}
return null;
}
This is suggested replaced with the following using LINQ:
private Ninja FindNinjaById(int ninjaId)
{
return Ninjas.FirstOrDefault(ninja => ninja.Id == ninjaId);
}
This looks all fine, and I'm sure it's no problem regarding performance to replace this one foreach. But is it something I should do in general? Or might I run into performance problems with all these LINQ queries everywhere?
LINQ syntax is typically less efficient than a foreach loop. It's good to be aware of any performance tradeoff that might occur when you use LINQ to improve the readability of your code. And if you'd like to measure the performance difference, you can use a tool like BenchmarkDotNet to do so.
Conclusion. It would seem the performance of LINQ is similar to more basic constructs in C#, except for that notable case where Count was significantly slower. If performance is important it's crucial to do benchmarks on your application rather than relying on anecdotes (including this one).
There are following disadvantages of using LINQ: LINQ is not good to write complex queries like SQL. LINQ doesn't take the full advantage of SQL features like cached execution plan for stored procedure. Performance is degraded if you don't write the LINQ query correctly.
You need to understand what the LINQ query is going to do "under the hood" and compare that to running your code before you can know whether you should change it. Generally, I don't mean that you need to know the exact code that will be generated, but you do need to know the basic idea of how it would go about performing the operation. In your example, I would surmise that LINQ would basically work about the same as your code and because the LINQ statement is more compact and descriptive, I would prefer it. There are times, though, when LINQ may not be the ideal choice, though probably not many. Generally I would think that just about any looping construct would be replaceable by an equivalent LINQ construct.
Let me start by saying that I love LINQ for its expressiveness and use it all the time without any problem.
There are however some differences in performance. Normally they are small enough to ignore, but in the critical path of your application, there might be times you want to optimize them away.
Here is the set of differences that you should be aware of, that could matter with performance:
GetEnumerator
method on an collection to iterate it. Calling GetEnumerator
usually ensures the creation of yet another object.IEnumerator
interface. Interface calls are a bit slower than normal method calls.IEnumerator
objects often need to be disposed or at least, Dispose
has to be called.When performance is a concern, also try using for
over foreach
.
Again, I love LINQ and I can't remember ever decided not to use a LINQ (to objects) query because of performance. So, don't do any premature optimizations. Start with the most readability solution first, than optimize when needed. So profile, profile and profile.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With