在null IEnumerables上为Count()返回零

时间:2010-08-19 08:23:36

标签: c# .net collections

我厌倦了使用这样的代码:

var count = 0;
if (myEnumerable != null)
{
    count = myEnumerable.Count();
}

这有点迂腐:

var count = (myEnumerable ?? new string[0]).Count();

这样做有什么比较整洁的方法吗?我曾经在IEnumerable<>上有一个(名字很糟的)PhantomCount扩展方法使用了我的第一个代码示例,但它有一些关于它的气味(除了名称)。

9 个答案:

答案 0 :(得分:32)

问题实际上在于创建这些枚举的任何内容。除非您有充分的理由,否则生成可迭代集合的任何内容都应返回空集合而不是null。这将与Null-Object-Pattern一致,因此好处是相同的。

我的建议是修复生成myEnumerable的内容,或者如果你不能这样做,请先添加一个检查方式,看看它是否为null并做出适当的反应。

答案 1 :(得分:14)

怎么样

count = myEnumerable == null? 0 : myEnumerable.Count()

答案 2 :(得分:9)

我认为使用扩展方法不是一个坏主意。

public static int NullableCount<T>(this IEnumerable<T> collection)
{
   return collection == null ? 0 : collection.Count();
}

答案 3 :(得分:5)

我使用自定义扩展方法:

public static IEnumerable<T> EmptyIfNull<T>(this IEnumerable<T> source)
{
    return source ?? Enumerable.Empty<T>();
}

...

int count = myEnumerable.EmptyIfNull().Count();

答案 4 :(得分:2)

只需创建自己的扩展方法即可根据需要处理空的枚举。

public int CountOrNull<T>(this IEnumerable<T> source)
{
    return source == null ? 0 : source.Count();
}

然后您可以使用:

var list1 = new int[] { 1, 2, 3, 4 };
var list2 = (int[])null;

var count1 = list1.CountOrNull(); // 4
var count2 = list2.CountOrNull(); // 0

这是扩展方法的好处。即使调用该方法的对象(您似乎是)null,它们仍然可以正常工作。

答案 5 :(得分:2)

我还会编写自己的扩展方法CountOrZeroForNull,如其他答案所示。

除了......而不是:

var count = (myEnumerable ?? new string[0]).Count();
                          // ^^^^^^^^^^^^^
你可以写:

var count = (myEnumerable ?? Enumerable.Empty<string>()).Count();
                          // ^^^^^^^^^^^^^^^^^^^^^^^^^^

这并不能缓解您的具体问题,但它会绕过未使用数组的分配。 (Enumerable.Empty<T>很可能是作为简单的yield break语句实现的。)

答案 6 :(得分:2)

在2019年,最简洁的方法是var count = myEnumerable?.Count() ?? 0;

答案 7 :(得分:1)

如果返回的值为0,您正在采取什么行动?

如果这很有趣,也许您应该像IsNullOrEmpty一样使用Haack的IEnumerable扩展方法:

public static bool IsNullOrEmpty<T>(this IEnumerable<T> items) 
{
    return items == null || !items.Any();
}

链接为http://haacked.com/archive/2010/06/10/checking-for-empty-enumerations.aspx

在博客上发表评论时,您还会找到我写的Exception课程:

public class ArgumentNullOrEmptyException : ArgumentNullException
{
    public ArgumentNullOrEmptyException( string paramName ) : base( paramName )
    {}

    public ArgumentNullOrEmptyException( string paramName, string message ) : base( paramName, message )
    {}

    public override string Message
    {
        get
        {
            return "Value cannot be null nor empty.{0}Parameter name: {1}".FormatWith( Environment.NewLine, ParamName );
        }
    }
}

答案 8 :(得分:-2)

var count = 0; 

if (myEnumerable != null) 
    count = myEnumerable.Count(); 

虽然它不像其他答案那样技术性,但它的可读性最高。