微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

performance – 渐近行为IEnumerable.Intersect vs HashedSet.IntersectWith

我已经阅读了很多关于HashSet和LINQ Set Operations的帖子和博客,我得到的印象是 linq交集方法内部使用散列集作为第一个集合,IEnumerable作为第二个集合.因此,两者之间的差异是linq交集的O(n m),而两个散列集之间的散列集交集的O(n).我可以得到确认吗?在MSDN中没有记录LINQ交叉的大O.

解决方法

嗯,它是特定于实现的,所以理论上它可能会改变 – 但基本上差别只是使用HashSet.Intersect,而你是从一个哈希集开始,所以你只需要迭代一个集合.

“明显的”实现将分别给出Intersect和IntersectWith的O(M N)和O(N)复杂度 – 当然,假设一个合适的哈希码.看到任何其他实现,我会非常惊讶,我当然没有看到任何证据表明任何版本的.NET都附带了其他任何东西.

可以说,如果Intersect的两个参数都已经是HashSet< T>你可以优化它来迭代较小的集合并检查每个元素是否在较大的集合中.但是,这还有另一个问题,即集合可能不会使用相同的比较器或相交调用.

有关详细信息,请参阅我的Edulinq implementation and post,其中包括有关MSDN中不准确的说明. MSDN claims(在撰写本文时):

When the object returned by this method is enumerated,Intersect enumerates first,collecting all distinct elements of that sequence. It then enumerates second,marking those elements that occur in both sequences. Finally,the marked elements are yielded in the order in which they were collected.

无论是在排序还是时间方面,这都不是真的:

>它是最初枚举的第二个(完全是在返回序列上首次调用MoveNext()时)>结果是在它首先迭代时产生的 – 它们是流式的,而不是MSDN声称的“标记一切然后产生结果”

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐