Запах кода - какой шаблон проектирования и как реализовать? - PullRequest
3 голосов
/ 14 марта 2012

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

public enum Category{
  Hot,
  New
}

public enum Sort{
  New,
  Rising,      
  ThisWeek
}

public String getUrl(Category category, Sort sort){
   validateCategorySortCombo(category, sort);
}

Обратите внимание на validateCategorySortCombo (Category, Sort).Сначала я должен проверить комбинацию Категория + Сортировка, поскольку некоторые из них недействительны.Например:

if(Category == "Hot" && Sort == "Rising"){
    ThrowInvalidCategorySortCombo("Can't use hot category with rising sort")
}  

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

Второй запах кода возникает, когда мне нужно проверитьи Категория, и Сортировка, чтобы построить мой URL, который будет передан обратно.В настоящее время я использую серию операторов переключения:

String url;
switch(category){
  case Hot:
     url += "www.site.com/hot/";
  case New:
     url += "www.site.com/new/";
}

switch(sort){
  case New:
    url += "?sort=rising";
  case ThisYear:
    url += "?sort=thisyear";
}

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

  1. Какой шаблон проектирования будет использован для решения моей проблемы?
  2. Как мне поступить в реализации шаблона проектирования?

Ответы [ 5 ]

3 голосов
/ 14 марта 2012

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

С учетом вышесказанного пара шаблонов, которые могут в конечном итоге оказатьсяполезными в вашей ситуации были бы Стратегия и Цепочка ответственности .

Идем дальше ...

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

  1. свести к минимуму изменения кода проверки при добавлении новой сортировки / категории
  2. свести к минимуму изменения в коде построения URL при добавлении новогоСортировка / Категория

Исходя из этих целей, придумайте общий подход.Например, мои мысли ...

  1. Если я разделю каждую проверку на отдельный класс, мне не нужно будет изменять существующие алгоритмы проверки при добавлении новой категории / сортировки.Все, что мне нужно сделать, это добавить новый алгоритм проверки или, возможно, удалить существующий, если он больше не применяется.(Это может быть излишним, но я не знаю, насколько сложными или сложными будут ваши алгоритмы проверки)
  2. Если каждая категория / сортировка знает, как предоставить свой собственный фрагмент URL, каждая новая категория или сортировка должнане влияют на возможность получения представлений URL существующих категорий или сортов.

Теперь вы можете больше думать о реализации (где у вас много вариантов).Например, вы могли бы расширить свои перечисления, чтобы каждое значение уже знало свой компонент url, например, так:

public enum Sort{
  New("?sort=new"),
  Rising("?sort=rising"),      
  ThisWeek("?sort=thisweek");


  private String urlComponent;
  public Sort(String urlComponent) {this.urlComponent = urlComponent;)
  public getUrlComponent() {return this.urlComponent;}
}

По этому маршруту вы всегда можете вызвать mySort.getUrlComponent(), который не нужно менять при добавлении/ удаление значений сортировки.Это конкретно решит вашу вторую проблему.

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

2 голосов
/ 14 марта 2012

как сказал М Платвоет:

import java.util.*;
enum Category {
    Hot(EnumSet.of(Sort.Rising)),New(EnumSet.of(Sort.ThisWeek,Sort.ThisYear));
    Category(EnumSet<Sort> legal) {
        this.legal.addAll(legal);
    }
    boolean isLegal(Sort sort) {
        return legal.contains(sort);
    }
    private final EnumSet<Sort> legal=EnumSet.noneOf(Sort.class);
}
enum Sort {
    New,Rising,ThisWeek,ThisYear;
}
public class So9706550 {
        static boolean isValid(Category category,Sort sort) {
            return category.isLegal(sort);
    }
    public static void main(String[] args) {
        System.out.println(isValid(Category.Hot,Sort.Rising));
        System.out.println(isValid(Category.Hot,Sort.ThisWeek));
    }
}
1 голос
/ 14 марта 2012

Просто перенесите проверку порядка сортировки в перечисление вашей категории.Так что это читает category.isValidSort(sort);

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

Я заметил, что вы не только проверяете входные данные, но и составляете строку URL на их основе. Это может быть немного чрезмерно, хотя выглядит как классический случай Abstract Factory . У вас могут быть абстрактные семейства категорий и конкретные реализации SortedCategories. Другое преимущество состоит в том, что вы можете явно вызвать исключение в HotRaisedFactory как недопустимую комбинацию этой категории и этой сортировки.

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

Для вашего первого беспокойства -

Вы можете определить валидатор, который может быть конкретно hashmap, ключом которого будет составление категорий и сортировок.

вы можете заполнить эту карту заранеедопустимые комбинации [можно подумать о жестко запрограммированном файле / файле конфигурации / периодическом обновлении и т. д.].

В вашем validateCategorySortCombo вы можете проверить, содержит ли на самом деле хэш-карту ключ?Если да, хорошо идти.

-

Map<Compositekey<Sort,Category>,Boolean> validOptions = new hashMap..

void validateCategorySortCombo(category, sort){

  if(validOptions.containskey(category,sort)){
     //good to go
  }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...