Когда вы используете отражение? Модели / анти-паттерны - PullRequest
30 голосов
/ 10 января 2009

Я понимаю API отражения (в c #), но я не уверен, в какой ситуации я бы использовал его. Какие есть паттерны - анти-паттерны для использования отражения?

Ответы [ 17 ]

1 голос
/ 10 января 2009

Главное место, где я использую рефлексию: извлечение типа из базы данных.

У меня есть класс, который должен знать, какую библиотеку вызывать. Помните, что по мере добавления новых инструментов в список класс должен распознавать новые инструменты без перекомпиляции, поэтому об операторе switch не может быть и речи.

Вместо этого я сохраняю строку отражения в БД, которая говорит классу «создать один из них ...» Поскольку я (программист) всегда гарантирую, что класс является производным от одного базового класса, идея работает. Это чисто и эффективно.

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

(введите голос мудрый, старый мудрец)
Отражение приходит с невероятной силой ... используйте силу с мудростью.

1 голос
/ 10 января 2009

Я прошел 2 года разработки, не понимая цели рефлексии. Он имеет очень узкое применение, но чрезвычайно эффективен, когда подходит для работы.

Я думаю, что я пытаюсь сказать, использовать это только тогда, когда вы уверены, что это единственный способ достичь того, что вы хотите.

1 голос
/ 10 января 2009

Я использую его в случае, аналогичном упомянутому Харпером Шелби, в котором файл конфигурации указывает во время выполнения, какой объект нужно создать. В моем конкретном случае нет ничего более сложного, чем фабрика - только набор классов, которые реализуют общий интерфейс, и простая функция, которая считывает файл конфигурации и создает надлежащий объект, возвращая интерфейс.

0 голосов
/ 20 ноября 2013

Лично я не часто этим пользуюсь. Я склонен использовать его, когда у меня нет другого способа что-то кодировать.

Вот простой пример:

public static void LogException(Exception exc, string source)
{
    try
    {
        // Logic for logging exceptions
    }
    catch(Exception ex)
    {
        //If logging fails  for some reason 
        //then we still log it using reflection
        LogException(ex, "Error while logging an exception");
    }
}
0 голосов
/ 15 марта 2012

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

0 голосов
/ 10 января 2009

Reflection позволяет решать проблемы, которые в противном случае потребовали бы дублирования кода. Если вы обнаружите, что копируете и вставляете код, и не видите, как может помочь шаблон OO, может быть, если вы сможете вызвать их, тогда «команда r» может помочь.

Только шучу. Я не мог понять смысл размышления целую вечность. Если вы можете написать код для выполнения работы, зачем вам вообще нужно использовать рефлексию?

Скажем, у вас много объектов с графическим интерфейсом, таких как формы или объекты таблиц. Он привязывается к бизнес-объекту как Клиент:

public class Customer
{
   public string FirstName;
   public string LastName;

}

Ваши пользователи не хотят видеть заголовки столбцов «FirstName» или «LastName». Они хотят «Христианское Имя» и Фамилия. Вы не хотите кодировать буквальные строки во всех ваших объектах GUI на случай, если они передумают на «Имя» и «Фамилия отца» (я знаю, пример дерьма).

Если вы определяете свой класс с помощью атрибутов:

public class Customer
{
   [Description("Christian Name")]
   public string FirstName;

   [Description("Surname")]
   public string LastName;

}

Вы можете использовать отражение, чтобы вытащить имена столбцов. Если вам нужно изменить способ, которым все ваши объекты графического интерфейса описывают объект клиента, вы теперь делаете это в одном месте.

Мне не известны какие-либо анти-паттерны. Мой совет - прыгнуть и попробовать. Вы начнете видеть все виды способов, которыми рефлексия дает вам элегантное решение. Производительность часто указывается в качестве причины, по которой не следует использовать повторное сравнение. С улучшением производительности возникают накладные расходы, но я бы не стал их учитывать, если только вы не докажете, что эти издержки наносят ущерб алгоритму, который вам нужен.

0 голосов
/ 10 января 2009

Я чаще всего использую его, когда мне нужно нарушить инкапсуляцию другого (обычно фреймворка). То есть мне нужно изменить какое-то личное поле, или вызвать частный метод, или создать экземпляр некоторого внутреннего класса в библиотеке, которую я не могу изменить. Хорошим примером является код в мой ответ на этот вопрос . В этом случае поведение каркасного метода ServiceBase.Run было неприемлемым, поэтому я использовал рефлексию, чтобы сделать то же самое, что и в более приемлемой манере.

У Reflection есть и много других применений, включая печать на утке , работа с атрибутами и поздняя привязка .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...