2013-02-20 123 views
3

我在那裏,我給一個對象,並需要將情況:轉換對象集合

  • 確定該物體是一個單一的對象或一個集合(數組,列表等)
  • 如果是一個集合,儘管列表中的一步。

我到目前爲止。測試IEnumerable不起作用。而轉換爲IEnumerable只適用於非原始類型。

static bool IsIEnum<T>(T x) 
{ 
    return null != typeof(T).GetInterface("IEnumerable`1"); 
} 
static void print(object o) 
{ 
    Console.WriteLine(IsIEnum(o));  // Always returns false 
    var o2 = (IEnumerable<object>)o;  // Exception on arrays of primitives 
    foreach(var i in o2) { 
     Console.WriteLine(i); 
    } 
} 
public void Test() 
{ 
    //int [] x = new int[]{1,2,3,4,5,6,7,8,9}; 
    string [] x = new string[]{"Now", "is", "the", "time..."}; 
    print(x);  
} 

任何人都知道如何做到這一點?

+3

如果你爲什麼地球上您使用的對象泛型?爲什麼不打印(T obj)?另外,你試過的是IEnumerable而不是GetInterface?並且爲了運行時檢查你不應該使用typeof,你應該使用GetType。 – 2013-02-20 16:22:40

+0

謝謝,所有。我用Snippet編譯器測試並沒有注意到它是「使用System.Collections.Generic;」默認。我曾嘗試過非泛型IEnumerable,並且在更改爲「使用System.Collections」之前出現錯誤。 – 2013-02-20 17:26:48

回答

6

這足以檢查對象是轉換到非通用IEnumerable接口:

var collection = o as IEnumerable; 
if (collection != null) 
{ 
    // It's enumerable... 
    foreach (var item in collection) 
    { 
     // Static type of item is System.Object. 
     // Runtime type of item can be anything. 
     Console.WriteLine(item); 
    } 
} 
else 
{ 
    // It's not enumerable... 
} 

IEnumerable<T>本身實現IEnumerable,因此這將爲通用和非通用工種的一致好評。使用此接口而不是通用接口避免了通用接口差異的問題:IEnumerable<T>不一定可轉換爲IEnumerable<object>

這個問題討論了通用接口方差在更多的細節:Generic Variance in C# 4.0

0

不要使用IEnumerable

static void print(object o) 
{ 
    Console.WriteLine(IsIEnum(o));  // Always returns false 
    var o2 = o as IEnumerable;  // Exception on arrays of primitives 
    if(o2 != null) { 
     foreach(var i in o2) { 
     Console.WriteLine(i); 
     } 
    } 
} 

通用版本,您將錯過某些類型的,可以在foreach如果你使用這樣做。可在foreach被用作收集的對象並不需要實現IEnumerable它只是需要實現GetEnumerator而這又需要返回具有Current屬性和MoveNext方法

如果集合鍵入一個類型而你只需要支持不同類型的集合,你可以在這種情況下做

static void print<T>(T o) { 
    //Not a collection 
} 

static void print<T>(IEnumerable<T> o) { 
    foreach(var i in o2) { 
     Console.WriteLine(i); 
    } 
} 

方法重載會接你取決於對象是否是一個集合了正確的方法(在這種情況下,通過定義實施IEnumerable<T>

0

使用下面的代碼:

Type t = typeof(System.Collections.IEnumerable); 

Console.WriteLine(t.IsAssignableFrom(T)); //returns true for collentions 
+0

字符串也實現'IEnumerable',所以你需要過濾字符串。 – Sam 2017-10-24 22:22:55