2010-11-02 21 views
5

Accedo al valor de la propiedad de un objeto de clase en tiempo de ejecución usando la reflexión en C#.C# - Obteniendo el valor de propiedad de la clase secundaria

public bool GetValue(string fieldName, out object fieldValue) 
    { 
     // Get type of current record 
     Type curentRecordType = _currentObject.GetType(); 
     PropertyInfo property = curentRecordType.GetProperty(fieldName); 

     if (property != null) 
     { 
      fieldValue = property.GetValue(_currentObject, null).ToString(); 
      return true; 
     } 
     else 
     { 
      fieldValue = null; 
      return false; 
     } 
    } 

Paso Nombre de la propiedad como parámetro: fieldName a este método. Ahora, necesito acceder a un valor de propiedad desde el objeto secundario de la clase anterior en tiempo de ejecución.
¿Alguien puede indicar cómo puedo acceder al valor de la propiedad del objeto secundario?

+0

¿Tienes algún problema o tienes otra pregunta aquí? – leppie

+0

edité mi pregunta, necesito una forma de acceder al valor de la propiedad del objeto hijo. – iniki

Respuesta

6

Dado que desea poder encontrar objetos en objetos secundarios anidados arbitrariamente, necesita una función que pueda llamar recursivamente. Esto se complica por el hecho de que puede tener hijos que vuelvan a referirse a sus padres, por lo que debe hacer un seguimiento de los objetos que ha visto antes en su búsqueda.

static bool GetValue(object currentObject, string propName, out object value) 
{ 
    // call helper function that keeps track of which objects we've seen before 
    return GetValue(currentObject, propName, out value, new HashSet<object>()); 
} 

static bool GetValue(object currentObject, string propName, out object value, 
        HashSet<object> searchedObjects) 
{ 
    PropertyInfo propInfo = currentObject.GetType().GetProperty(propName); 
    if (propInfo != null) 
    { 
     value = propInfo.GetValue(currentObject, null); 
     return true; 
    } 
    // search child properties 
    foreach (PropertyInfo propInfo2 in currentObject.GetType().GetProperties()) 
    { // ignore indexed properties 
     if (propInfo2.GetIndexParameters().Length == 0) 
     { 
      object newObject = propInfo2.GetValue(currentObject, null); 
      if (newObject != null && searchedObjects.Add(newObject) && 
       GetValue(newObject, propName, out value, searchedObjects)) 
       return true; 
     } 
    } 
    // property not found here 
    value = null; 
    return false; 
} 

Si sabe qué niño objeto Su propiedad está en que sólo puede pasar la ruta al mismo, así:

public bool GetValue(string pathName, out object fieldValue) 
{ 
    object currentObject = _currentObject; 
    string[] fieldNames = pathName.Split("."); 

    foreach (string fieldName in fieldNames) 
    { 
     // Get type of current record 
     Type curentRecordType = currentObject.GetType(); 
     PropertyInfo property = curentRecordType.GetProperty(fieldName); 

     if (property != null) 
     { 
      currentObject = property.GetValue(currentObject, null).ToString(); 
     } 
     else 
     { 
      fieldValue = null; 
      return false; 
     } 
    } 
    fieldValue = currentObject; 
    return true; 
} 

en lugar de llamarlo como GetValue("foo", out val) que lo llamarían como GetValue("foo.bar", out val).

+0

dando el nombre de ruta para cada propiedad no es posible en mi caso ya que hay cientos de propiedades. Quiero una forma breve y eficiente en la que mi código pueda pasar al objeto hijo y recuperar el valor de la propiedad, dando solo el nombre principal de objeto y propiedad como entrada. – iniki

+0

Entonces, ¿está diciendo que tiene un árbol de objetos donde cada propiedad entre todos los objetos tiene un nombre único, y desea poder encontrar una propiedad anidada arbitrariamente solo con su nombre? (si tiene foo.bar.baz.qux, solo quiere pasar "qux" y hacer que la función descubra que está dentro de 'foo.bar.baz ') – Gabe

+0

sí, necesita ingresar solo el objeto principal y el Nombre de la propiedad – iniki

0

Obtiene el objeto secundario usando reflexión, luego usa el reflejo para obtener el valor de la misma manera.

+0

¿te refieres al uso de GetNestedTypes()? – iniki

0
public void Main(){ 
    var containerObject = new ContainerObject(); 
    object propertyValue; 
    object nestedPropertyValue; 
    if(GetValue(containerObject, "FirstPropertyName", out propertyValue){ 
     bool success = GetValue(propertyValue, "NestedPropertyName", out nestedPropertyValue); 
    } 

} 

public bool GetValue(object currentObject, string propertyName, out object propertyValue) 
{ 
    // Get type of current record 
    var currentObjectType = currentObject.GetType(); 
    PropertyInfo propertyInfo = currentObjectType.GetProperty(propertyName); 

    propertyValue = propertyInfo != null 
        ? propertyInfo.GetValue(currentObject,null) 
        : null; 
    return propertyValue == null; 
} 
+0

Gracias smartcaveman, pero no anticipo qué propiedad particular del objeto principal será padre para la propiedad anidada. En cuyo caso, su fragmento de código no resolverá mi problema. – iniki

+0

Puede obtener todas las propiedades usando GetProperties en lugar de GetProperty (nombre). Podría ayudarte más si especificas más el objetivo. – smartcaveman

Cuestiones relacionadas