2010-11-02 2 views
5

Я получаю доступ к значению свойства из объекта класса во время выполнения, используя отражение в C#.C# - Получение значения свойства из дочернего класса

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; 
     } 
    } 

Передаю имя свойства как параметр: fieldName к этому методу. Теперь мне нужно получить доступ к значению свойства из дочернего объекта вышеуказанного класса во время выполнения.
Может ли кто-нибудь там указать, как я могу получить доступ к стоимости объекта объекта?

+0

У вас есть проблема или есть другой вопрос здесь? – leppie

+0

отредактировал мой вопрос, нужен способ получить доступ к значению свойства дочернего объекта. – iniki

ответ

6

Поскольку вы хотите, чтобы находить объекты на произвольно вложенных дочерних объектах, вам нужна функция, которую вы можете вызывать рекурсивно. Это осложняется тем фактом, что у вас могут быть дети, которые обращаются к родителям, поэтому вам нужно отслеживать, какие объекты вы видели ранее в своем поиске.

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; 
} 

Если вы знаете, что ребенок возражает ваше имущество в вы можете просто передать путь к нему, например, так:

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; 
} 

Вместо того, чтобы называть его как GetValue("foo", out val) вы могли бы назвать его как GetValue("foo.bar", out val).

+0

указание имени пути для каждого свойства невозможно в моем случае, так как есть сотни свойств. Хотите короткий и эффективный способ, когда мой код может перейти к дочернему объекту и получить значение свойства, введя только исходное имя объекта и свойства в качестве входных данных. – iniki

+0

Значит, вы говорите, что у вас есть дерево объектов, где каждое свойство из всех объектов имеет уникальное имя, и вы хотите найти произвольно вложенное свойство с указанием только его имени? (если у вас есть foo.bar.baz.qux, вы хотите просто передать «qux» и выяснить, что функция находится в 'foo.bar.baz ') – Gabe

+0

да, нужно ввести только основной объект и имя свойства – iniki

0

Получить дочерний объект, используя отражение, а затем использовать отражение, чтобы получить значение таким же образом.

+0

Вы имеете в виду, используя 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

Спасибо smartcaveman, но я не заранее, какое конкретное свойство основного объекта будет родителем для вложенного свойства. В этом случае ваш фрагмент кода не решит мою проблему. – iniki

+0

Вы можете получить все свойства, используя GetProperties вместо GetProperty (имя). Я мог бы помочь вам больше, если бы вы указали цель. – smartcaveman

Смежные вопросы