У меня есть несколько классов, которые я хочу отметить с конкретным атрибутом. Я имею два подхода в виду. Каждый включает использование расширяющего Атрибут класса. Другое использование пустой интерфейс:
Атрибуты
public class FoodAttribute : Attribute { }
[Food]
public class Pizza { /* ... */ }
[Food]
public class Pancake { /* ... */ }
if (obj.IsDefined(typeof(FoodAttribute), false)) { /* ... */ }
Интерфейс
public interface IFoodTag { }
public class Pizza : IFoodTag { /* ... */ }
public class Pancake : IFoodTag { /* ... */ }
if (obj is IFoodTag) { /* ... */ }
Я не решаюсь использовать атрибуты из-за его использования Отражения. В то же время, однако, я колеблюсь при создании пустого интерфейса, который только действительно служит тегом. Я протестировал на напряжение оба, и разница во времени между этими двумя является только приблизительно тремя миллисекундами, таким образом, производительность не под угрозой здесь.
Ну, с атрибутами, вы всегда можете создавать атрибут таким образом, чтобы его функция не распространяется на типы потомков автоматически.
с интерфейсами, это невозможно.
Я бы пошел с атрибутами.
Я должен сказать иначе. Я думаю, что для вашего примера , интерфейс маркера имеет больше смысла.
Это потому, что кажется весьма вероятным , что вы можете однажды добавить некоторых членов в IFood
.
Ваш дизайн начинается так:
interface IFood {}
Но затем вы решаете добавить что-то туда:
interface IFood {
int Calories { get; }
}
Есть также другие способы для расширения интерфейсов :
static class FoodExtensions {
public static void Lighten(this IFood self) {
self.Calories /= 2;
}
}
В этом случае, как вы говорите, вы не используете интерфейс правильно.
Что случилось с использованием отражения получение вас приписывает? Обычный ответ является исполнением, но это обычно - не реальная проблема почти во всех случаях.
Вы, вероятно, ответили на ваш вопрос своим собственным. Атрибуты здесь более логичны, отражение не является большим монстром с красными глазами =)
BTW, вы можете показать вызова код, где вы определяете помеченные типы интерфейсов? Разве вы не используете отражение там?