对于仅执行一项操作而言,哪种 C# 容器的资源效率最高?
我发现自己经常遇到需要对一组属性执行操作的情况。该操作可以是任何内容,从检查特定属性是否与集合中的任何内容匹配到单个操作迭代。有时,该集合是在调用函数时动态生成的,有些是使用简单的 LINQ 语句构建的,其他时候它是一个始终保持不变的硬编码集合。但有一个常量始终存在:该集合仅针对一项操作而存在,并且在其之前或之后没有任何用处。
我的问题是,我的应用程序中有很多点需要这样做,但我存储这些集合的方式似乎非常非常不一致。其中一些是数组,一些是列表,刚才我发现了几个链接列表。现在,我特别关心的操作都不必关心索引、容器大小、顺序或任何单个容器类型赋予的任何其他功能。我选择资源效率是因为这比掷硬币更好。我想,由于数组大小已配置并且它是一个非常基本的容器,这可能是我的最佳选择,但我认为四处询问是一个更好的主意。或者,如果有一个更好的选择,不是出于资源效率,而是严格来说是针对这种情况的更好选择,那也很好。
I find myself often with a situation where I need to perform an operation on a set of properties. The operation can be anything from checking if a particular property matches anything in the set to a single iteration of actions. Sometimes the set is dynamically generated when the function is called, some built with a simple LINQ statement, other times it is a hard-coded set that will always remain the same. But one constant always exists: the set only exists for one single operation and has no use before or after it.
My problem is, I have so many points in my application where this is necessary, but I appear to be very, very inconsistent in how I store these sets. Some of them are arrays, some are lists, and just now I've found a couple linked lists. Now, none of the operations I'm specifically concerned about have to care about indices, container size, order, or any other functionality that is bestowed by any of the individual container types. I picked resource efficiency because it's a better idea than flipping coins. I figured, since array size is configured and it's a very elementary container, that might be my best choice, but I figure it is a better idea to ask around. Alternatively, if there's a better choice not out of resource-efficiency but strictly as being a better choice for this kind of situation, that would be nice as well.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
您承认这更多的是关于编码一致性而不是性能或效率,我认为一般做法是使用
List
。它的实际后备存储是一个数组,因此容器开销并没有真正损失太多(如果有什么值得注意的话)。如果没有更多的资格,我不确定我能提供更多的东西。当然,如果您确实不关心问题中列出的内容,只需将变量键入
IEnumerable
,并且您只在处理实际容器时填充它;你在哪里消费它将会完全一致。With your acknowledgement that this is more about coding consistency rather than performance or efficiency, I think the general practice is to use a
List<T>
. Its actual backing store is an array, so you aren't really losing much (if anything noticable) to container overhead. Without more qualifications, I'm not sure that I can offer anything more than that.Of course, if you truly don't care about the things that you list in your question, just type your variables as
IEnumerable<T>
and you're only dealing with the actual container when you're populating it; where you consume it will be entirely consistent.关于资源效率,有两个基本原则需要注意。
你说索引和顺序并不重要,频繁的操作就是匹配。
Dictionary
(这是一个哈希表)是一个此类工作的理想人选。键的查找速度非常快,这对您的匹配操作很有帮助。缺点是它会消耗比严格要求多一点的内存。通常的负载系数约为 0.8,因此我们并不是在谈论大幅增长或其他任何情况。对于其他操作,您可能会发现数组或
List
是更好的选择,特别是在您不需要快速查找的情况下。只要您不需要特殊操作(查找、排序等)的高性能,那么就很难超越基于数组的容器的一般资源特性。There are two basic principles to be aware of regarding resource efficiency.
You said that indices and order do not matter and that a frequent operation is matching. A
Dictionary<T>
(which is a hashtable) is an ideal candidate for this type of work. Lookups on the keys are very fast which would be beneficial in your matching operation. The disadvantage is that it will consume a little more memory than what would be strictly required. The usual load factor is around .8 so we are not talking about a huge increase or anything.For your other operations you may find that an array or
List<T>
is a better option especially if you do not need to have the fast lookups. As long as you are not needing high performance on specialty operations (lookups, sorting, etc.) then it is hard to beat the general resource characteristics of array based containers.总的来说,列表可能没问题。它很容易理解(在文学编程意义上)并且相当高效。如果您添加具有重复键的条目,键控集合(例如 Dict、SortedList)将引发异常,尽管这对于您现在正在处理的工作来说可能不是问题。
只有当您发现遇到 CPU 时间或内存大小问题时,您才应该考虑提高“效率”,并且只有在确定这是瓶颈之后。
无论您使用哪种方法,如果应用程序运行足够长的时间,仍然会创建和删除最终将被垃圾收集的底层对象(集合或迭代器)。
List is probably fine in general. It's easy to understand (in the literate programming sense) and reasonably efficient. The keyed collections (e.g. Dict, SortedList) will throw an exception if you add an entry with a duplicate key, though this may not be a problem for what you're working on now.
Only if you find that you're running into a CPU-time or memory-size problem should you look at improving the "efficiency", and then only after determining that this is the bottleneck.
No matter which approach you use, there will still be creation and deletion of the underlying objects (collection or iterator) that will eventually be garbage collected, if the application runs long enough.