Как создать интерфейс метода с переменными параметрами/сигнатурами разных методов?
Я пытаюсь создать интерфейс для общего класса, но классы реализации могут иметь разные параметры.
например.
public interface IViewModel
{
//...
void ResetReferences();
}
// and then, in my class implementations, something like this:
public class LocationViewModel : IViewModel
{
public void ResetReferences(List<StateProvinces> stateProvinces) //...
}
public class ProductViewModel : IViewModel
{
public void ResetReferences(List<Color> colors, List<Size> sizes) //...
}
Поэтому обратите внимание, что я хочу стандартизировать соглашение об именах "RestReferences". Я уверен, что не могу этого сделать, но есть ли шаблон дизайна, который мог бы работать? например в моем интерфейсе, что-то вроде ниже?
// variable parameters
void ResetReferences(params object[] list);
Но как я могу заставить проверять тип или вызвать фактическую подпись метода, которую я хочу, и т.д.
Может быть, интерфейс неправильный? Может быть, просто базовый класс и некоторые условные обозначения?
Спасибо,
Ответы
Ответ 1
Замените ваши списки args объектами, которые реализуют связанный интерфейс:
public interface IViewModel
{
//...
void ResetReferences(IResetValues vals);
}
Я должен добавить, что IMO, "ResetReferences()" не должен принимать аргумент... он должен reset для некоторого значения по умолчанию, которое будет специфично для отдельных типов (типов), которые реализуют ваш интерфейс... "Reset" - это слово, которое для меня означает "восстановить исходное состояние"... добавление args подразумевает, что вы можете контролировать это.
Ответ 2
Цель интерфейса - информировать клиентский код об интерфейсе и не обращать внимания на его реализацию. Если ваши реализации требуют специальной обработки при вызове, код клиента должен знать, какую реализацию он вызывает, а затем вся цель интерфейса теряется.
Если я не полностью пойму, что вы пытаетесь сделать, вы не по пути.
Ответ 3
Если параметры могут быть разными, то это не общий интерфейс. Положите это так: нужно ли вызывающему абоненту знать класс реализации? Если это так, вы потеряли преимущества связи с интерфейсом.
Один из вариантов - инкапсулировать параметры в другой тип и сделать класс общим для этого типа. Например:
public interface IViewModel<T>
{
void ResetReferences(T data);
}
Затем вы инкапсулируете List<Color> colors, List<Size> sizes
в один тип и, возможно, поместите List<StateProvinces> stateProvinces
в другой.
Это несколько неудобно, хотя...
Ответ 4
Вам нужно будет реализовать метод интерфейса, но вы все равно можете сделать то, что хотите
public class LocationViewModel : IViewModel
{
public void ResetReferences(List<StateProvinces> stateProvinces) // ...
void IViewModel.ResetReferences() // ...
}
Ответ 5
Вам нужно будет иметь оба метода в интерфейсе (и некорректный для экземпляра исключить не поддерживаемое исключение), или интерфейс наследует от двух других интерфейсов к одному и тому же эффекту.
Определение интерфейса - это целая подпись.
Также возможно передать объект как параметр (возможно, полученный из базового класса ParameterProvider), чтобы объект инкапсулировал динамическую природу и все еще позволяет статическому интерфейсу. Но в этом случае вы все равно работаете над системой типов.