2017-06-30 81 views
0

每當我編程C#時,我都會很好地使用Linq,因爲我喜歡它,它讓我像一個功能程序員一樣思考,我經常發現比命令式編程更容易。一項公約我創建對象的隨機列表時經常使用如下:如何創建一個一般創建一系列對象的方法?

var animals= Enumerable.Range(0, 100).Select(n => new Animal()).ToList(); 

我知道這是(可能慢)語法糖for循環,增加了項目到列表。這對我來說是完全可以接受的,因爲它不會冒犯我的靈敏度。這裏是我不喜歡的:

var animals = Enumerable.Range(0,100)。 選擇(n =>新動物())。 ToList();

我想做一個幫手Func這樣做,甚至更少的打字。理想情況下,我想鍵入:

var animals = NewRange(0, 100, Animal); 

但是我越來越掛斷瞭如何做到這一點(如果它甚至可能)。我可以使用反射和各種其他粗糙的東西(yuck!),但沒有這些,我無法弄清楚。這是我得到的最接近的:

public Func<int, Type, List<object>> NewRange = (n, t) => Enumerable.Range(0, n).Select(o => new t()).ToList(); 

但是,這不會編譯(顯而易見的原因)。有人對我如何創建自己的便捷功能有了一些建議?

回答

2

所以,你最終只是想要一個IEnumerable,使用默認構造函數的n個實例全部初始化?

大約是這樣的內容:

public static List<T> CreateList<T>(int numberOfItems) where T : new() 
{  
    var result = new List<T>(numberOfItems); 
    for (int ix = 0; ix < numberOfItems; ix++) 
    { 
     result.Add(new T()); 
    } 
    return result; 
} 
+0

其實他想要一個'List <>'。 – NetMage

+0

好的。更新以替代返回列表。 –

+0

你的風格與我的非常不同:)。我建議設置'List'容量,因爲你知道它的開始。 – NetMage

0

剛剛嘗試這樣的事:

public static List<T> NewRange<T>(int n) where T: new() 
{ 
    return Enumerable.Range(0, n).Select(_ => new T()).ToList(); 
} 

或者與表達濃郁的成員:

public static List<T> NewRange<T>(int n) where T : new() => 
     Enumerable.Range(0, n).Select(_ => new T()).ToList(); 

並使用它:

var animals = NewRange<Animal>(100); 
+0

通過7秒打我! ;-) –

+0

我很驚訝,你發佈7秒後的答案,然後@Tim張貼5秒後:) –

+0

好的答案,將工作,但類似於下面我不知道爲什麼Range方法是有用的(除了事實上它被用在問題中)。它是爲增加列表而設計的,這對於這個用例來說似乎很奇怪。 –

2

你需要一個類型限制ensu重新您可以實例T,所以:

List<T> NewRange<T>(int howMany) where T : new() 
{ 
    return Enumerable.Range(0, howMany).Select(n => new T()).ToList(); 
} 

而且你可以用它喜歡:

var animals = NewRange<Animal>(100); 
+0

好,快速的回答。我不喜歡使用Enumerable.Range,儘管你並不需要一系列遞增數字。 –

0

你可以傳遞一個lambda你的函數來創建新的對象:

public static List<T> NewRange<T>(int n, Func<T> NewObject) { 
    return Enumerable.Range(0, n).Select(_ => NewObject()).ToList(); 
} 

然後調用它像:

var Animals = NewRange(10,() => new Animal()); 
0

林不知道你是否可以管理你的問題沒有任何反思

這裏是一個小例子,你可以如何與一個泛型類型simplyfy它:

public void Main() 
{ 
    var animals = NewRange<Animal>(0, 100); 
} 

public static List<T> NewRange<T>(int n, int b) 
{ 
    return (List<T>)Enumerable.Range(n, b).Select(instance => (T)Activator.CreateInstance(typeof(T))).ToList(); 
} 

我希望這將正確地回答你的問題,將適合您的需要

+0

參數n和b在您的功能中沒有用處。像其他人一樣,新的約束是一個更清潔的方法。 – CSharpie