公共方法的收益率反模式?

时间:2015-03-19 21:00:04

标签: c# performance yield yield-return

yield return是一种非常好的语法,可以快速编写过滤器或映射,这些过滤器或映射对于使用Linq语句来说太过分了。这就是为什么我经常写这样的方法:

public IEnumerable<Person> GetFilteredPersons()
{
    foreach ( var person in _Persons )
    {
        // [Semi-expensive logic]
        yield return person;
    }
}

问题是这个方法的用户不知道当他在obj.GetFilteredPersons()上多次迭代时,他正在浪费不必要的CPU。它甚至可能意味着当他认为他正在进行两次简单的O(n)迭代时,他实际上进行了两次O(n^2)次迭代。

问题

该类是否有责任仅公开O(n)个枚举器,我希望在返回'yielding'IEnumerable之前总是调用ToList()? 当用户只想迭代一次时,调用一个ToList()的(小)缺点?

或者我应该将此决定留给本课程的用户,并让他们在迭代之前决定是否要ToList结果?

假设我们正在讨论高性能环境。

1 个答案:

答案 0 :(得分:12)

如果用户知道它需要多次枚举返回的集合并且不想重新计算,那么用户有责任调用ToList()从声明为返回IEnumerable<T>的方法返回的值。值。

在这些情况下,甚至会有ReSharper显示的警告。

此外,将决策推送给调用者可以提供更大的灵活性,因为在某些情况下,您不会受到CPU的限制,但是您会限制内存使用,并且您可以做额外的计算,以防止发生额外的分配。