C# LINQ:为什么数组和列表使用不同的迭代器

C# LINQ:为什么数组和列表使用不同的迭代器,c#,.net,performance,linq,C#,.net,Performance,Linq,问题是:它为什么使用这个代码 if (source is TSource[]) return (IEnumerable<TResult>) new Enumerable.WhereSelectArrayIterator<TSource, TResult>((TSource[]) source, (Func<TSource, bool>) null, selector); if (source is List<TSource>)

问题是:它为什么使用这个代码

  if (source is TSource[])
    return (IEnumerable<TResult>) new Enumerable.WhereSelectArrayIterator<TSource, TResult>((TSource[]) source, (Func<TSource, bool>) null, selector);
  if (source is List<TSource>)
    return (IEnumerable<TResult>) new Enumerable.WhereSelectListIterator<TSource, TResult>((List<TSource>) source, (Func<TSource, bool>) null, selector);
  else
    return (IEnumerable<TResult>) new Enumerable.WhereSelectEnumerableIterator<TSource, TResult>(source, (Func<TSource, bool>) null, selector);
}
if(源为TSource[])
返回(IEnumerable)新的可枚举项。其中SelectArrayInterator((TSource[])source,(Func)null,selector);
如果(来源是列表)
返回(IEnumerable)新的可枚举项。其中SelectListIterator((列表)源,(Func)null,选择器);
其他的
返回(IEnumerable)新的可枚举项。其中SelectEnumerableInterator(源,(Func)null,选择器);
}
而不是

  if (source is IList<TSource>)
    return (IEnumerable<TResult>) new Enumerable.WhereSelectIListIterator<TSource, TResult>((List<TSource>) source, (Func<TSource, bool>) null, selector);
  return (IEnumerable<TResult>) new Enumerable.WhereSelectEnumerableIterator<TSource, TResult>(source, (Func<TSource, bool>) null, selector);
}
if(源代码为IList)
返回(IEnumerable)新的可枚举项。其中SelectilisTiterator((列表)源,(Func)null,选择器);
返回(IEnumerable)新的可枚举项。其中SelectEnumerableInterator(源,(Func)null,选择器);
}

我的意思是
List
T[]
都实现了
IList
,它们都有索引器和实现
IEnumerable
,因此它们都可以以相同的单数方式进行迭代,但现在使用不同的迭代器

这只是一种优化,涵盖了过滤数组或列表的极为常见的情况

  • 其中SelectArrayInterator不使用数组的基础枚举数-它使用索引器。从性能的角度来看,直接使用数组索引器比使用
    IList
    索引器或枚举器更好

  • 其中SelectListIterator确实使用列表的枚举数,但因为它“知道”列表的枚举数类型是结构<代码>列表。枚举数(它可以使用与接口方法分离的<代码>列表上的特殊GetEnumerator方法进行检索),它避免了将枚举数装箱到堆上——如果使用
    IEnumerator
    ,则必须这样做

  • 其中SelectEnumerableIterator是使用源代码的backing
    IEnumerator
    的一般情况-它将适用于所有类型的序列,但无需任何特殊优化。如果枚举数恰好是一个结构,那么很不幸,它将被装箱


  • 您从哪里获得这些代码片段?我可以想象,在使用这些迭代器的情况下,LINQ可以进行合理的优化,并且可能不会以完全相同的方式进行迭代。但是如果不挖掘LINQ的来源,我无法证明这一点,只是一个强烈的预感(因此,一个评论)@payo是的,我几分钟前就知道了。因此,如果同一个想法在同一时间出现在不同的人身上,可能是正确的。