Выделенный параметр класса - PullRequest
1 голос
/ 24 сентября 2010

У меня есть интерфейс

 interface IRepository<T>
 {
     List<T> GetAll(string id)
     List<T> GetAll(string id, string desc)
     List<T> GetAll(string id, string desc, int[] status)
     List<T> GetAll(string id, string desc, int[] status, ....)
 }

Многие из моих классов реализовывали этот интерфейс. Моя проблема, чаще всего, когда клиенты запрашивают настройку, мне обычно нужно добавлять параметры в методы. Поэтому, когда у меня есть 10 классов, реализующих этот интерфейс, мне также нужно обновить каждый из классов, наследующих интерфейс (я использую абстрактный шаблон фабрики), что довольно сложно. И это также не очень приятно для глаз, видя перегрузку многих методов, как в примере выше, IMO. Есть ли какое-либо решение / обходной путь, чтобы сделать параметры динамическими (кроме опции param [], которая мне не нравится). Я имею в виду как выделенный параметр класса / интерфейса, так что мне не нужно перегружать метод при добавлении параметра. Что-то вроде этого

  interface IRepository<T>
  {
     List<T> GetAll(Parameter args);
  }

класс Paramter (или, может быть, интерфейс)

  static class Parameter
  {
     public string Id { get; set; }
     public string Desc { get; set; }
     public int[] Status { get; set; }
  }

пример реализации клиентами

  class Client1Accounts : IRepository<Employee>
  {
      List<Employee> GetALl(Parameter param)
      {
           return DataFactory.GetAllById(param.Id);
       }   
  }

  class Client2Accounts : IRepository<Employee>
  {
      List<Employee> GetALl(Parameter param)
      {
           return DataFactory.GetAllByDesc(param.Desc);
       }   
  }


  class Client2Accounts : IRepository<Employee>
  {
      List<Employee> GetALl(Parameter param)
      {
           int[] status = { 99, 88 }
           return DataFactory.GetAllFiltered(param.Id, param.Desc, status);
       }   
  }

Таким образом, когда мне нужно добавить параметр, мне просто нужно добавить другое свойство в класс параметров

  static class Parameter
  {
     public string Id { get; set; }
     public string Desc { get; set; }
     public int[] Status { get; set; }
     public long newLongParam { get; set; }
  }

Правильный ли этот подход? какие-нибудь другие идеи?

Ответы [ 3 ]

1 голос
/ 24 сентября 2010

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

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

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

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

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

(Если вас интересует шаблон «представьте новый тип», в структуре есть примеры - ProcessStartInfo, возможно, лучший из тех, о которых я могу сразу думать.)

0 голосов
/ 13 марта 2012

Вы можете сделать 1 метод с 1 параметром. Этот 1 параметр является строковым массивом. Вот как работает основная функция во многих p-языках. Но это может раздражать приведение всех параметров к строкам и к строкам, особенно когда у вас есть параметры массива и объекта.

0 голосов
/ 24 сентября 2010

Как насчет этого:

public interface IRepository<T>
{
    IQueryable<T> GetAll();
}
...