Как получить доступ к свойствам Динамически / поздно связан?
-
01-10-2019 - |
Вопрос
Я хотел бы реализовать метод, который позволяет мне получить доступ к свойству неизвестного / анонимного объекта (-Графа) в поздний связанный / динамичный способ (я даже не знаю, как правильно назвать его).
Вот пример того, что я хотел бы достичь:
// setup an anonymous object
var a = new { B = new { C = new { I = 33 } } };
// now get the value of a.B.C.I in a late-bound way
var i = Get(a, "B.C.I");
И вот простая реализация с использованием «классического» отражения:
public static object Get(object obj, string expression)
{
foreach (var name in expression.Split('.'))
{
var property = obj.GetType().GetProperty(name);
obj = property.GetValue(obj, null);
}
return obj;
}
Какие еще варианты у меня есть с C # / .NET 4, чтобы реализовать что-то подобное, как показано выше, но, возможно, проще, больше исполнителю и т. Д.?
Может быть, есть способы достичь того же, что позволило бы мне указать expression
используя лямбда выражение вместо строки? Экспрессивные деревья будут полезными любым способом (например, как показано в этот вопрос)?
Обновлять: Объект и выражение передаются в мой код через веб-сервис. Вот почему я использовал object
а также string
в моем Get()
метод.
Решение
Ты фактически Только есть выражение как строку? Это известно при компиляционном времени, только что сами типы не известны (или трудно выразить)? Если так:
dynamic d = a;
int i = d.B.C.I;
если ты В самом деле Только у него в качестве строки (например, в качестве введенных пользователем данных), которые делают жизнь намного сложнее, и ни один из функций C # 4 действительно поможет вам. Вы могли бы потенциально оценить его как сценарий Ironpython или что-то в этом роде ...
Редактировать: Хорошо, после обновления звучит так, как будто вы находитесь в последней ситуации - в этом случае я не знаю более приятного пути, чем использование отражения. Некоторые из встроенного обязательства недвижимости, построенные для UIS, могут помочь, но я не знаю чистого способа доступа к нему.
Другие советы
Если вы хотите использовать стиль C #, вы можете использовать компилятор MONO как услуг из вашего приложения. Я опишу, как это сделать здесь:Mono Compiler в качестве услуги (MCS)
В качестве альтернативного подхода вы можете использовать отражение, чтобы поставить все свойства вашего объекта в развертывание, затем используйте его как словарь (потому что расширенные продукты Idectionary). В качестве альтернативы вы можете использовать json.net и звонить JObject.FromObject
, который превратит регулярный объект в работу, который доступен в словаре, подобном словарю (и в качестве дополнительной выгоды имеет рекурсивную поддержку графика). Наконец, вы можете использовать тот же подход для сброса вашего объекта в словарь словарей.