When calling Any() on a null object, it throws an ArgumentNullException in C#. If the object is null, there definitely aren't 'any', and it should probably return false.
Why does C# behave this way?
When calling Any() on a null object, it throws an ArgumentNullException in C#. If the object is null, there definitely aren't 'any', and it should probably return false.
Why does C# behave this way?
With modern C#, you can easily handle the OP's scenario with a simple check like this:
List<string> foo = null;
if (foo?.Any() ?? false)
{
DoStuff();
}
This is kinda like a lame AnyOrDefault(bool default) implementation that the OP is expecting the Any() extension method to do.
You could easily make this into an extension like this:
public static bool HasItems<T>(this IEnumerable<T> source)
{
return (source?.Any() ?? false);
}
Honestly, I don't really like the name Renamed to AnyOrDefault for this since it won't ever make sense to pass in a default value (a default of true would probably be pretty mean to people reading code later).HasItems, as suggested in the comments. This is a far better name!
Any() is an extension method that throws ArgumentNullException if the source is null. Would you perform an action on nothing? In general, it's better to get some explicit indicator of what's happening in the code rather than the default value.
But it doesn't mean it can't be like that. If you know what you doing, write your own custom implementation.
I just wanted to share with you some practical advice my company is following.
We write our custom packages shared with private NuGet that are widely used in our products. Checking if the list is null/empty is very frequent, so we decided to write our implementation of Any which makes our code shorter and simpler.
Any() internally attempts to access the underlying sequence (IEnumerable). Since the object can be null, there is no way to access the enumerable to validate it, hence a NullReferenceException is thrown to indicate this behavior.
At first, it sounds like it should just return false since null in a way could mean none.
However, there is different levels of information and behavior occurring here.
Any() with 0 elements is a collection with 0 elements.null means no collection.Any() with 0 elements is a collection. The latter isn't a collection.
If you have a wallet (underlying sequence), with no cash (elements) inside, you have a wallet, but your broke (no elements). Null means you don't even have a wallet to put cash inside.