.net Array 与 List<T>:何时使用哪个?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/434761/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Array versus List<T>: When to use which?
提问by Frederick The Fool
MyClass[] array;
List<MyClass> list;
What are the scenarios when one is preferable over the other? And why?
当一种比另一种更可取的情况是什么?为什么?
采纳答案by Marc Gravell
It is rare, in reality, that you would want to use an array. Definitely use a List<T>any time you want to add/remove data, since resizing arrays is expensive. If you know the data is fixed length, and you want to micro-optimise for some very specificreason (after benchmarking), then an array may be useful.
实际上,您很少会想要使用数组。一定List<T>要随时使用 a来添加/删除数据,因为调整数组大小很昂贵。如果您知道数据是固定长度的,并且出于某些非常具体的原因(在基准测试之后)想要进行微优化,那么数组可能很有用。
List<T>offers a lotmore functionality than an array (although LINQ evens it up a bit), and is almost always the right choice. Except for paramsarguments, of course. ;-p
List<T>提供一个很多比数组更多的功能(尽管LINQ找齐它一点),而且几乎总是正确的选择。params当然,争论除外。;-p
As a counter - List<T>is one-dimensional; where-as you have have rectangular (etc) arrays like int[,]or string[,,]- but there are other ways of modelling such data (if you need) in an object model.
作为计数器 -List<T>是一维的;哪里 - 因为你有像int[,]或这样的矩形(等)数组string[,,]- 但是还有其他方法可以在对象模型中对此类数据(如果需要)进行建模。
See also:
也可以看看:
That said, I make a lotof use of arrays in my protobuf-netproject; entirely for performance:
也就是说,我在protobuf-net项目中大量使用数组;完全为了性能:
- it does a lot of bit-shifting, so a
byte[]is pretty much essential for encoding; - I use a local rolling
byte[]buffer which I fill before sending down to the underlying stream (and v.v.); quicker thanBufferedStreametc; - it internally uses an array-based model of objects (
Foo[]rather thanList<Foo>), since the size is fixed once built, and needs to be very fast.
- 它做了很多位移,所以 a
byte[]对于编码非常重要; - 我使用本地滚动
byte[]缓冲区,在发送到底层流(和 vv)之前填充它;比BufferedStream等更快; - 它在内部使用基于数组的对象模型(
Foo[]而不是List<Foo>),因为大小一旦构建就固定了,并且需要非常快。
But this is definitely an exception; for general line-of-business processing, a List<T>wins every time.
但这绝对是个例外;对于一般业务线处理,List<T>每次都是一个胜利。
回答by Jon Skeet
Really just answering to add a link which I'm surprised hasn't been mentioned yet: Eric's Lippert's blog entry on "Arrays considered somewhat harmful."
真的只是回答添加一个链接,我很惊讶还没有提到:Eric 的 Lippert 的博客文章“数组被认为有些有害”。
You can judge from the title that it's suggesting using collections wherever practical - but as Marc rightly points out, there are plenty of places where an array really is the only practical solution.
您可以从标题判断它建议在任何可行的地方使用集合 - 但正如 Marc 正确指出的那样,有很多地方数组确实是唯一实用的解决方案。
回答by Alnitak
Notwithstanding the other answers recommending List<T>, you'll want to use arrays when handling:
尽管有其他推荐的答案List<T>,但您在处理时仍需要使用数组:
- image bitmap data
- other low-level data-structures (i.e. network protocols)
- 图像位图数据
- 其他低级数据结构(即网络协议)
回答by Spencer Ruport
Unless you are really concerned with performance, and by that I mean, "Why are you using .Net instead of C++?" you should stick with List<>. It's easier to maintain and does all the dirty work of resizing an array behind the scenes for you. (If necessary, List<> is pretty smart about choosing array sizes so it doesn't need to usually.)
除非你真的很关心性能,我的意思是“你为什么使用 .Net 而不是 C++?” 你应该坚持使用 List<>。它更易于维护,并为您完成在幕后调整数组大小的所有肮脏工作。(如有必要, List<> 在选择数组大小方面非常聪明,因此通常不需要。)
回答by Herman Schoenfeld
Arrays shouldbe used in preference to List when the immutability of the collection itself is part of the contract between the client & provider code (not necessarily immutability of the items within the collection) AND when IEnumerable is not suitable.
当集合本身的不变性是客户端和提供者代码之间契约的一部分(不一定是集合中的项目的不变性)并且当 IEnumerable 不适合时,应该优先使用数组而不是 List。
For example,
例如,
var str = "This is a string";
var strChars = str.ToCharArray(); // returns array
It is clear that modification of "strChars" will not mutate the original "str" object, irrespective implementation-level knowledge of "str"'s underlying type.
很明显,“strChars”的修改不会改变原始的“str”对象,而不管“str”底层类型的实现级别知识。
But suppose that
但假设
var str = "This is a string";
var strChars = str.ToCharList(); // returns List<char>
strChars.Insert(0, 'X');
In this case, it's not clear from that code-snippet alone if the insert method will or will not mutate the original "str" object. It requires implementation level knowledge of String to make that determination, which breaks Design by Contract approach. In the case of String, it's not a big deal, but it can be a big deal in almost every other case. Setting the List to read-only does help but results in run-time errors, not compile-time.
在这种情况下,仅凭该代码片段并不清楚插入方法是否会改变原始“str”对象。它需要 String 的实现级别知识来做出决定,这打破了按契约设计的方法。在 String 的情况下,这不是什么大问题,但在几乎所有其他情况下都可能是大问题。将 List 设置为只读确实有帮助,但会导致运行时错误,而不是编译时错误。
回答by smack0007
If I know exactly how many elements I'm going to need, say I need 5 elements and only ever5 elements then I use an array. Otherwise I just use a List<T>.
如果我知道我到底有多少元素去需求,说我需要5元,仅过5元,然后我使用一个数组。否则我只使用 List<T>。
回答by Sune Rievers
Most of the times, using a Listwould suffice. A Listuses an internal array to handle its data, and automatically resizes the array when adding more elements to the Listthan its current capacity, which makes it more easy to use than an array, where you need to know the capacity beforehand.
大多数情况下,使用 aList就足够了。AList使用内部数组来处理它的数据,并在List向其添加比当前容量更多的元素时自动调整数组的大小,这使得它比数组更易于使用,您需要事先知道容量。
See http://msdn.microsoft.com/en-us/library/ms379570(v=vs.80).aspx#datastructures20_1_topic5for more information about Lists in C# or just decompile System.Collections.Generic.List<T>.
有关C# 中列表的更多信息,请参阅http://msdn.microsoft.com/en-us/library/ms379570(v=vs.80).aspx#datastructures20_1_topic5或仅反编译System.Collections.Generic.List<T>。
If you need multidimensional data (for example using a matrix or in graphics programming), you would probably go with an arrayinstead.
如果您需要多维数据(例如使用矩阵或在图形编程中),您可能会array改用 。
As always, if memory or performance is an issue, measure it! Otherwise you could be making false assumptions about the code.
与往常一样,如果内存或性能是一个问题,请测量它!否则,您可能会对代码做出错误的假设。
回答by Melbourne Developer
Arrays Vs. Lists is a classic maintainability vs. performance problem. The rule of thumb that nearly all developers follow is that you should shoot for both, but when they come in to conflict, choose maintainability over performance. The exception to that rule is when performance has already proven to be an issue. If you carry this principle in to Arrays Vs. Lists, then what you get is this:
数组对比 列表是一个典型的可维护性与性能问题。几乎所有开发人员都遵循的经验法则是,您应该为两者都努力,但是当它们发生冲突时,选择可维护性而不是性能。该规则的例外情况是性能已被证明是一个问题。如果你把这个原则应用到 Arrays Vs 中。列表,那么你得到的是:
Use strongly typed lists until you hit performance problems. If you hit a performance problem, make a decision as to whether dropping out to arrays will benefit your solution with performance more than it will be a detriment to your solution in terms of maintenance.
使用强类型列表,直到遇到性能问题。如果您遇到性能问题,请决定退出阵列是否对您的解决方案的性能有益,而不是在维护方面对您的解决方案造成损害。
回答by iliketocode
Lists in .NET are wrappers over arrays, and use an array internally. The time complexity of operations on lists is the same as would be with arrays, however there is a little more overhead with all the added functionality / ease of use of lists (such as automatic resizing and the methods that come with the list class). Pretty much, I would recommend using lists in all cases unless there is a compelling reason notto do so, such as if you need to write extremely optimized code, or are working with other code that is built around arrays.
.NET 中的列表是数组的包装器,并在内部使用数组。列表操作的时间复杂度与数组相同,但是所有添加的功能/列表的易用性(例如自动调整大小和列表类附带的方法)会增加一些开销。几乎,我建议在所有情况下都使用列表,除非有令人信服的理由不这样做,例如如果您需要编写极其优化的代码,或者正在使用围绕数组构建的其他代码。
回答by supercat
Another situation not yet mentioned is when one will have a large number of items, each of which consists of a fixed bunch of related-but-independent variables stuck together (e.g. the coordinates of a point, or the vertices of a 3d triangle). An array of exposed-field structures will allow the its elements to be efficiently modified "in place"--something which is not possible with any other collection type. Because an array of structures holds its elements consecutively in RAM, sequential accesses to array elements can be very fast. In situations where code will need to make many sequential passes through an array, an array of structures may outperform an array or other collection of class object references by a factor of 2:1; further, the ability to update elements in place may allow an array of structures to outperform any other kind of collection of structures.
另一种尚未提及的情况是当一个人将拥有大量项目时,每个项目都由一组固定的相关但独立的变量组成(例如,一个点的坐标,或 3d 三角形的顶点)。一组暴露的字段结构将允许其元素被有效地“就地”修改——这是任何其他集合类型都无法实现的。由于结构数组在 RAM 中连续保存其元素,因此对数组元素的顺序访问可以非常快。在代码需要对数组进行多次顺序传递的情况下,结构数组的性能可能比数组或其他类对象引用集合的性能高 2:1;更远,
Although arrays are not resizable, it is not difficult to have code store an array reference along with the number of elements that are in use, and replace the array with a larger one as required. Alternatively, one could easily write code for a type which behaved much like a List<T>but exposed its backing store, thus allowing one to say either MyPoints.Add(nextPoint);or MyPoints.Items[23].X += 5;. Note that the latter would not necessarily throw an exception if code tried to access beyond the end of the list, but usage would otherwise be conceptually quite similar to List<T>.
尽管数组不可调整大小,但让代码存储数组引用以及正在使用的元素数量并根据需要用更大的数组替换数组并不困难。或者,人们可以轻松地为一种行为很像 aList<T>但暴露其后备存储的类型编写代码,从而允许人们说MyPoints.Add(nextPoint);or 或MyPoints.Items[23].X += 5;。请注意,如果代码尝试访问列表末尾以外的内容,后者不一定会抛出异常,但用法在概念上与List<T>.

