在集合类型上使用支撑初始化程序是否设置了初始容量?

在集合类型上使用支撑初始化程序是否设置了它的容量,或者您是否仍需要指定它?

那就是:

var list = new List(){ "One", "Two" }; 

结果与此相同:

 var list = new List(2){ "One", "Two" }; 

对象初始化程序只需为每个项目调用Add

 var list = new List{ "One", "Two", "Three" }; 

如您所见,在这种情况下,无参数构造函数被调用:

 L_0000: nop L_0001: newobj instance void [mscorlib]System.Collections.Generic.List`1::.ctor() L_0006: stloc.1 L_0007: ldloc.1 L_0008: ldstr "One" L_000d: callvirt instance void [mscorlib]System.Collections.Generic.List`1::Add(!0) L_0012: nop L_0013: ldloc.1 L_0014: ldstr "Two" L_0019: callvirt instance void [mscorlib]System.Collections.Generic.List`1::Add(!0) L_001e: nop L_001f: ldloc.1 L_0020: ldstr "Three" L_0025: callvirt instance void [mscorlib]System.Collections.Generic.List`1::Add(!0) L_002a: nop L_002b: ldloc.1 

所以,你应该手动设置容量:

 var list = new List(5){ "One", "Two", "Three" }; 

编译成:

 L_0000: nop L_0001: ldc.i4.5 L_0002: newobj instance void [mscorlib]System.Collections.Generic.List`1::.ctor(int32) // rest is same 

因此,算法非常明显 – 它调用您指定的构造函数(默认情况下无参数),然后为每个项调用Add

注意:我知道, List默认容量是4,我validation了如果我们在初始化程序中传递超过4个项目会发生什么(例如,编译器可能根据项目计数确定调用哪个构造函数)但结果是相同的 – 无参数构造函数默认情况下调用。

我认为集合初始化程序的目的是创建小集合(1-8项),因此会有一点性能影响(如果你将8个项目传递给初始化程序,只有一个resize)。 没有人希望您将使用100个项目进行就地初始化。 如果你打算这样做,你应该使用适当的集合构造函数。

集合初始值设定项使用可用的Add方法将项添加到集合中。 因此,行为与使用空构造函数调用Add方法相同。

实际上,编译器会将对象初始化程序语法更改为对Add方法的调用。 因此, 您是否使用对象初始化程序是无关紧要的 。 重要的是你是否决定使用构造函数重载和实际添加的项目数量。

根据文档并考虑到对象初始化器的计数为2,它最终也将设置容量。

容量始终大于或等于Count

使用无参数构造函数初始化List后,内部数组将设置为长度为0的数组。

调用Add(),Insert()或InsertRange()时,将重新计算列表的容量:

  • 如果列表中没有其他元素,则容量设置为4(默认容量)。
  • 如果有其他元素,则容量设置为元素数量的两倍。

如果指定容量,则以该大小创建内部数组。

参考文献:DotNet来源:RefSrc \ Source.NET 4.5 \ 4.5.50709.0 \ net \ ndp \ clr \ src \ BCL \ System \ Collections \ Generic \ List.cs \ 597531 \ List.cs