В javascript вы можете определить, определено ли свойство с помощью неопределенного ключевого слова:
if( typeof data.myProperty == "undefined" ) ...
Как бы вы сделали это в C #, используя динамическое ключевое слово с ExpandoObject
и без исключения?
c#
dynamic
expandoobject
Softlion
источник
источник
data.myProperty
; он проверяет, чтоtypeof data.myProperty
возвращается. Это верно, чтоdata.myProperty
может существовать и быть установленнымundefined
, но в этом случаеtypeof
будет возвращать что-то отличное от"undefined"
. Так что этот код работает.Ответы:
Согласно MSDN декларация показывает, что он реализует IDictionary:
Вы можете использовать это, чтобы увидеть, определен ли член:
источник
Важное различие должно быть сделано здесь.
Большинство ответов здесь относятся только к ExpandoObject, который упоминается в вопросе. Но обычное использование (и причина для поиска этого вопроса при поиске) - использование ASP.Net MVC ViewBag. Это пользовательская реализация / подкласс DynamicObject, которая не будет генерировать исключение, когда вы проверяете любое произвольное имя свойства на null. Предположим, вы можете объявить свойство как:
Затем предположим, что вы хотите проверить его значение, и установлено ли оно - существует ли оно. Следующее действительно, скомпилирует, не выдаст никаких исключений и даст правильный ответ:
Теперь избавьтесь от объявления EnableThinger. Тот же код компилируется и работает правильно. Не нужно размышлять.
В отличие от ViewBag, ExpandoObject будет выдавать, если вы проверяете на null свойство, которое не существует. Чтобы получить более мягкую функциональность MVC ViewBag из ваших
dynamic
объектов, вам нужно использовать динамическую реализацию, которая не генерирует.Вы можете просто использовать точную реализацию в MVC ViewBag:
https://github.com/ASP-NET-MVC/aspnetwebstack/blob/master/src/System.Web.Mvc/DynamicViewDataDictionary.cs
Вы можете увидеть его привязанным к MVC Views здесь, в MVC ViewPage:
http://aspnetwebstack.codeplex.com/SourceControl/latest#src/System.Web.Mvc/ViewPage.cs
Ключом к изящному поведению DynamicViewDataDictionary является реализация словаря в ViewDataDictionary, здесь:
https://github.com/ASP-NET-MVC/aspnetwebstack/blob/master/src/System.Web.Mvc/ViewDataDictionary.cs
Другими словами, он всегда возвращает значение для всех ключей, независимо от того, что в нем находится - он просто возвращает ноль, когда там ничего нет. Но ViewDataDictionary имеет бремя привязки к модели MVC, поэтому лучше исключить только изящные части словаря для использования вне MVC Views.
Слишком долго, чтобы действительно публиковать здесь все кишки - большинство из них просто реализуют IDictionary - но вот динамический объект (класс
DDict
), который не генерирует нулевые проверки свойств, которые не были объявлены, на Github:https://github.com/b9chris/GracefulDynamicDictionary
Если вы просто хотите добавить его в свой проект через NuGet, его имя GracefulDynamicDictionary .
источник
Недавно я ответил на очень похожий вопрос: как мне отразить элементы динамического объекта?
Вкратце, ExpandoObject - не единственный динамический объект, который вы можете получить. Отражение будет работать для статических типов (типов, которые не реализуют IDynamicMetaObjectProvider). Для типов, которые реализуют этот интерфейс, отражение в основном бесполезно. Для ExpandoObject вы можете просто проверить, определено ли свойство как ключ в базовом словаре. Для других реализаций это может быть сложно, а иногда единственный способ - работать с исключениями. Для получения подробной информации перейдите по ссылке выше.
источник
ОБНОВЛЕНО: Вы можете использовать делегаты и пытаться получить значение из свойства динамического объекта, если оно существует. Если свойства нет, просто перехватите исключение и верните false.
Посмотрите, у меня все работает нормально:
Вывод кода следующий:
источник
IsPropertyExist
. В этом примере вы знаете, что можно броситьInvalidOperationException
. На практике вы не представляете, какое исключение может быть выдано. +1, чтобы противодействовать культу груза.Я хотел создать метод расширения, чтобы я мог сделать что-то вроде:
... но вы не можете создавать расширения в
ExpandoObject
соответствии с документацией C # 5 (подробнее здесь ).В итоге я создал помощника класса:
Чтобы использовать это:
источник
Почему вы не хотите использовать Reflection, чтобы получить набор свойств типа? Как это
источник
Этот метод расширения проверяет наличие свойства, а затем возвращает значение или ноль. Это полезно, если вы не хотите, чтобы ваши приложения выдавали ненужные исключения, по крайней мере, те, которые вы можете помочь.
Если можно использовать как таковой:
или если ваша локальная переменная является «динамической», вам придется сначала привести ее к ExpandoObject.
источник
В зависимости от вашего варианта использования, если null может рассматриваться как совпадающий с undefined, вы можете превратить ваш ExpandoObject в DynamicJsonObject.
Вывод:
источник
источник
Эй, ребята, прекратите использовать Reflection для всего, что стоит много циклов ЦП.
Вот решение:
источник
Попробуй это
источник
dynamic
объектами (всегда возвращаетnull
).