在C#中初始化Generic.List

时间:2009-04-15 14:34:32

标签: c# .net generics constructor

在C#中,我可以使用以下语法初始化列表。

List<int> intList= new List<int>() { 1, 2, 3 };

我想知道{}语法是如何工作的,以及它是否有名称。有一个构造函数需要IEnumerable,你可以调用它。

List<int> intList= new List<int>(new int[]{ 1, 2, 3 });

这似乎更“标准”。当我解构List的默认构造函数时,我只看到

this._items = Array.Empty;

我希望能够做到这一点。

CustomClass abc = new CustomClass() {1, 2, 3};

并且能够使用1, 2, 3列表。这是如何工作的?

更新

Jon Skeet回答

  

它正在调用无参数   构造函数,然后调用Add:

> List<int> tmp = new List<int>();
> tmp.Add(1); tmp.Add(2); tmp.Add(3);
> List<int> intList = tmp;

我明白这是做什么的。我想知道怎么做。该语法如何知道调用Add方法?

更新

我知道,接受Jon Skeet的回答是多么陈词滥调。但是,字符串和整数的例子很棒。另外一个非常有用的MSDN页面是:

7 个答案:

答案 0 :(得分:65)

这称为集合初始值设定项。它调用无参数构造函数,然后调用Add:

List<int> tmp = new List<int>();
tmp.Add(1);
tmp.Add(2);
tmp.Add(3);
List<int> intList = tmp;

该类型的要求是:

  • 它实现了IEnumerable
  • 它具有Add的重载,适用于您提供的参数类型。您可以在大括号中提供多个参数,在这种情况下,编译器会查找具有多个参数的Add方法。

例如:

public class DummyCollection : IEnumerable
{
    IEnumerator IEnumerable.GetEnumerator()
    {
        throw new InvalidOperationException("Not a real collection!");
    }

    public void Add(string x)
    {
        Console.WriteLine("Called Add(string)");
    }

    public void Add(int x, int y)
    {
        Console.WriteLine("Called Add(int, int)");
    }
}

然后您可以使用:

DummyCollection foo = new DummyCollection
{
    "Hi",
    "There",
    { 1, 2 }
};

(当然,通常您希望您的收藏集正确实施IEnumerable ...)

答案 1 :(得分:7)

阅读 Object and Collection Initializers (C# Programming Guide) 。基本上你可以使用每个自定义类型作为列表(实现IEnumerable)。

答案 2 :(得分:4)

他们被称为collection initializers(另请参阅here),他们的工作方式是寻找可以进行出价的Add()方法。它为花括号中的每个整数调用Add()

搜索Add()方法纯粹是编译魔术。找到一个具有该名称的方法是硬编码的。

答案 3 :(得分:2)

您正在寻找的名称是“Collection Initializer”。它通过在集合类型上查找名为Add的方法并为您指定的每个值调用它来工作。

更多详情:Object and Collection Initializers (C# Programming Guide)

答案 4 :(得分:1)

我相信它是.Add方法的捷径。我从来没试过覆盖它,所以我不知道它是否可能。

答案 5 :(得分:0)

就我而言,通过对象初始化添加项目会搜索方法Add。因此,如List&lt; int&gt;将具有无效的Add(int),它将起作用。

要在课堂上使用它,只需添加

即可
class CustomClass { 
   public void Add(int num) {
      // Your code here
   }
}

正如Hallgrim指出的那样,你的类应该实现IEnumerable。

答案 6 :(得分:0)

它实际上是使用.Add方法。这意味着它为构造函数内括号中的每个项调用.Add