rspec/rules/S6617/why-dotnet.adoc
2023-06-05 10:57:04 +02:00

18 lines
1.4 KiB
Plaintext

== Why is this an issue?
When testing if a collection contains a specific item by simple equality, both `ICollection.Contains(T item)` and `IEnumerable.Any(x => x == item)` can be used. However, `Any` searches the data structure in a linear manner using a foreach loop, whereas `Contains` is considerably faster in some collection types, because of the underlying implementation. More specifically:
- `HashSet<T>` is a hashtable, and therefore has an O(1) lookup
- `SortedSet<T>` is a red-black tree, and therefore has a O(logN) lookup
- `List<T>` is a linear search, and therefore has an O(N) lookup, but the EqualityComparer is optimized for the `T` type, which is not the case for `Any`
For small collections, the performance difference may be negligible, but for large collections, it can be noticeable.
=== What is the potential impact?
We measured a significant improvement both in execution time and memory allocation. For more details see the `Benchmarks` section from the `More info` tab.
=== Exceptions
Since `https://learn.microsoft.com/en-us/dotnet/framework/data/adonet/ef/language-reference/linq-to-entities[LINQ to Entities]` relies a lot on `System.Linq` for https://learn.microsoft.com/en-us/dotnet/framework/data/adonet/ef/language-reference/linq-to-entities#query-conversion[query conversion], this rule won't raise when used within LINQ to Entities syntaxes.