2009-03-10 32 views
42

Estoy tratando de realizar la siguiente conversiónmoldeada recibido objeto a una lista de <object> o IEnumerable <object>

private void MyMethod(object myObject) 
{ 
    if(myObject is IEnumerable) 
    { 
     List<object> collection = (List<object>)myObject; 
     ... do something 
    } 
    else 
    { 
     ... do something 
    } 
} 

Pero siempre terminan con la siguiente excepction:

No se puede convertir objeto de tipo ' System.Collections.Generic.List 1[MySpecificType]' to type 'System.Collections.Generic.List 1 [System.Object] '

Realmente necesito que esto funcione, porque este método debe ser muy genérico para recibir objetos individuales y colecciones de tipos no especificados.

Esto es posible, o hay otra forma de lograr esto.

Gracias.

Respuesta

50

C# 4 tendrá los parámetros de plantilla covariantes y contravariantes, pero hasta entonces hay que hacer algo no genérico como

IList collection = (IList)myObject; 
+0

Gracias. Esto lo hizo. –

+1

@Sergio, debe comprobar que myObject implementa IList en lugar de IEnumerable antes de la conversión si desea evitar el riesgo de errores de tiempo de ejecución. Muchas colecciones incorporadas implementan IEnumerable pero no IList (por ejemplo, Dictionary <>, HashSet <>, Hashtable, Queue, Stack, etc.). – LukeH

+0

@Luke: si es una lista (que está implícita en la pregunta), implementará IList. – erikkallen

2

¿Qué tal

List<object> collection = new List<object>((IEnumerable)myObject); 
46

No se puede emitir un IEnumerable <T> a una lista <T>.

Pero se puede lograr esto usando LINQ:

var result = ((IEnumerable)myObject).Cast<object>().ToList(); 
+0

Éste también funciona. Gracias. –

+2

Esto también está creando una nueva lista, en lugar de lanzar la original. –

6

es lo que realmente necesita Más información que simple IEnumerable te da? Simplemente échalo a eso y usa foreach con él. Enfrentaré exactamente la misma situación en algunos bits de Protocol Buffers, y descubrí que el casting a IEnumerable (o IList para acceder a él como una lista) funciona muy bien.

9

El problema es que estás tratando de cambiar a un objeto más rico. Sólo tiene que añadir los elementos a una nueva lista:

if (myObject is IEnumerable) 
{ 
    List<object> list = new List<object>(); 
    var enumerator = ((IEnumerable) myObject).GetEnumerator(); 
    while (enumerator.MoveNext()) 
    { 
     list.Add(enumerator.Current); 
    } 
} 
+0

es esto funciona? –

0

Este Código trabajó para mí

List<Object> collection = new List<Object>((IEnumerable<Object>)myObject); 
1

tiene que unirse a la diversión ...

private void TestBench() 
    { 
     // An object to test 
     string[] stringEnumerable = new string[] { "Easy", "as", "Pi" }; 

     ObjectListFromUnknown(stringEnumerable); 
    } 

    private void ObjectListFromUnknown(object o) 
    { 
     if (typeof(IEnumerable<object>).IsAssignableFrom(o.GetType())) 
     { 
      List<object> listO = ((IEnumerable<object>)o).ToList(); 
      // Test it 
      foreach (var v in listO) 
      { 
       Console.WriteLine(v); 
      } 
     } 
    } 
0

tiene que escribir emitir usando como operador como este.

private void MyMethod(object myObject) 
{ 
if(myObject is IEnumerable) 
{ 
    List<object> collection = myObject as(List<object>); 
    ... do something 
} 
else 
{ 
    ... do something 
} 
}  
Cuestiones relacionadas