2009-06-01 16 views
13

(abreviado) de código ..PropertyInfo.GetValue() - ¿cómo se indexa en un parámetro genérico utilizando la reflexión en C#? Este

for (int i = 0; i < count; i++) 
{ 
    object obj = propertyInfo.GetValue(Tcurrent, new object[] { i }); 
} 

.. está lanzando un 'TargetParameterCountException: recuento de falta de coincidencia de parámetros' excepción.

El tipo subyacente de 'propertyInfo' es una colección de algunos T. 'count' es el número de elementos de la colección. Necesito iterar a través de la colección y realizar una operación en obj.

Asesoramiento apreciado.

Respuesta

19

La reflexión solo funciona en un nivel a la vez.

Está intentando indexar en la propiedad, eso está mal.

En su lugar, lea el valor de la propiedad y el objeto que recibe, ese es el objeto que necesita para indexar.

He aquí un ejemplo:

using System; 
using System.Collections.Generic; 
using System.Reflection; 

namespace DemoApp 
{ 
    public class TestClass 
    { 
     public List<Int32> Values { get; private set; } 

     public TestClass() 
     { 
      Values = new List<Int32>(); 
      Values.Add(10); 
     } 
    } 

    class Program 
    { 
     static void Main() 
     { 
      TestClass tc = new TestClass(); 

      PropertyInfo pi1 = tc.GetType().GetProperty("Values"); 
      Object collection = pi1.GetValue(tc, null); 

      // note that there's no checking here that the object really 
      // is a collection and thus really has the attribute 
      String indexerName = ((DefaultMemberAttribute)collection.GetType() 
       .GetCustomAttributes(typeof(DefaultMemberAttribute), 
       true)[0]).MemberName; 
      PropertyInfo pi2 = collection.GetType().GetProperty(indexerName); 
      Object value = pi2.GetValue(collection, new Object[] { 0 }); 

      Console.Out.WriteLine("tc.Values[0]: " + value); 
      Console.In.ReadLine(); 
     } 
    } 
} 
+2

bien, entiendo, gracias por la respuesta. ahora está funcionando, pero estaría interesado en conocer la propiedad "Artículo" si alguien lo sabe ... – flesh

+0

Lo encontró, cambió la respuesta. El atributo estaba en la clase, no en la propiedad. Tenga en cuenta que las clases que no tienen un indexador tampoco tienen el atributo. –

+0

observado - hago el control de cobro más arriba en mi código. gracias por la actualización :) – flesh

2

yo era la mayor parte del camino hasta que vi esto, y estoy publicando esto porque no he visto en ningún otro lugar; la clave estaba usando GetValue (colección, nuevo Objeto [] {i}); en el ciclo en lugar de tratar de usar GetValue (colección, nuevo Objeto [i]); fuera del circuito. (Probablemente puede ignorar el "resultado" en mi ejemplo);

private static string Recursive(object o) 
{ 
     string output=""; 
     Type t = o.GetType(); 
     if (t.GetProperty("Item") != null) 
     { 
      System.Reflection.PropertyInfo p = t.GetProperty("Item"); 
      int count = -1; 
      if (t.GetProperty("Count") != null && 
       t.GetProperty("Count").PropertyType == typeof(System.Int32)) 
      { 
       count = (int)t.GetProperty("Count").GetValue(o, null); 
      } 
      if (count > 0) 
      { 
       object[] index = new object[count]; 
       for (int i = 0; i < count; i++) 
       { 
        object val = p.GetValue(o, new object[] { i }); 
        output += RecursiveWorker(val, p, t); 
       } 
      } 
     } 
     return output;   
} 
0
Assembly zip_assembly = Assembly.LoadFrom(@"C:\Ionic.Zip.Reduced.dll"); 
Type ZipFileType = zip_assembly.GetType("Ionic.Zip.ZipFile"); 
Type ZipEntryType = zip_assembly.GetType("Ionic.Zip.ZipEntry"); 
string local_zip_file = @"C:\zipfile.zip"; 
object zip_file = ZipFileType.GetMethod("Read", new Type[] { typeof(string) }).Invoke(null, new object[] { local_zip_file }); 

// Entries is ICollection<ZipEntry> 
IEnumerable entries = (IEnumerable)ZipFileType.GetProperty("Entries").GetValue(zip_file, null); 
foreach (object entry in entries) 
{ 
    string file_name = (string)ZipEntryType.GetProperty("FileName").GetValue(entry, null); 
    Console.WriteLine(file_name); 
} 
Cuestiones relacionadas