Перевод текста на русский язык:
} }
//Если число не делится ни на какое другое число, кроме 1 и самого себя
if (multiples.isEmpty()) return ReportResult.create(number);
return ReportResult.create(numberWordMap, multiples, number);
}
}
NumberWordMap
используется для определения соответствия между особыми числами и словами, например, в данном случае «3» соответствует «Fizz», а «5» — «Buzz». Почему я не использую LinkedHashMap напрямую?
Вместо этого я создаю ещё одну абстрактную структуру данных. Очевидно, что возможностей чистых классов Map в Java недостаточно для решения этой задачи.
public class NumberWordMap {
public static int MAX_NUMBER = 9;
public static int MIN_NUMBER = 1;
private LinkedHashMap<Integer, String> map = new LinkedHashMap<Integer, String>();
/**
* @param specialNumber
* @param word
* @return
* @throws SpecialNumberIllegalException
*/
public NumberWordMap put(int specialNumber, String word) {
if (specialNumber < MIN_NUMBER || specialNumber > MAX_NUMBER)
throw new SpecialNumberIllegalException("number will be one of " + MIN_NUMBER + "..." + MAX_NUMBER + " integer");
map.put(specialNumber, word);
return this;
}
public boolean isContainsFirstSpecialNumber(int number) {
return (number + "").contains(getFirstNumber() + "");
}
.
.
.
.
}
Вы увидите, что я возвращаю класс ReportResult
, а не строку. Это сделано с учётом того, что пользователь (расширитель) может использовать не только «1», «Fizz» и «Buzz», но и другие строки. Поэтому ReportResult
сохраняет исходное число и соответствующий отчёт, например, ReportResult
в этом примере будет содержать одновременно 21 и FizzWhizz.
Таким образом, пользователь может реализовать свою логику экспорта, реализовав интерфейс Exporter
и метод export(ReportResult result)
. Я предоставляю стандартный экспортёр командной строки:
package com.thoughtworks.FizzBuzzWhizz.internal;
public class ConsoleExporter implements Exporter {
@Override
public void export(ReportResult result) {
System.out.println(result.getWord());
}
}
Думаю, читатель немного запутался. Давайте перейдём к основной программе:
NumberWordMap map = new NumberWordMap().put(3, "Fizz").put(5, "Buzz").put(7, "Whizz");
Game game = new Game(map, 1, 100);
game.exportTo(new ConsoleExporter()).start();
Глядя на этот код, вы, вероятно, понимаете мою идею. Теперь давайте посмотрим на метод start
класса Game
:
public void start() {
for (int i = startNumber; i <= endNumber; i++) {
exporter.export(Reporter.report(i, numberWordMap));
}
}
Теперь вы должны понимать мой дизайн. Этот дизайн имеет больше преимуществ по сравнению с первой реализацией: он проще в тестировании!
Это мой окончательный дизайн. Стоит отметить, что при разработке часто приходится балансировать между сложностью и гибкостью. Чрезмерное стремление к гибкости часто приводит к увеличению сложности, поэтому мы должны стремиться к повышению гибкости без увеличения сложности.
По сравнению с первым дизайном, второй дизайн добавил некоторую сложность ради гибкости. На самом деле, если это просто простая игра, которая не предназначена для реального бизнеса, то в этом нет необходимости, и даже есть некоторый избыточный дизайн. Конечно, это всего лишь игрушечная программа.
Вы также заметили, что на протяжении всего текста я не упоминал о шаблонах проектирования в своём коде, потому что мне не нравится говорить о шаблонах. Шаблоны проектирования — это готовые решения для определённых задач. Когда вы понимаете суть проблемы, шаблоны проектирования становятся очевидными.
Сегодня уже крайний срок сдачи работы. Вы сдали свою работу? Я тоже хотел бы посмотреть на ваш код и учиться вместе!
Все изображения взяты из сети, если у вас есть какие-либо вопросы по авторским правам, пожалуйста, свяжитесь со мной.
Вы можете оставить комментарий после Вход в систему
Неприемлемый контент может быть отображен здесь и не будет показан на странице. Вы можете проверить и изменить его с помощью соответствующей функции редактирования.
Если вы подтверждаете, что содержание не содержит непристойной лексики/перенаправления на рекламу/насилия/вульгарной порнографии/нарушений/пиратства/ложного/незначительного или незаконного контента, связанного с национальными законами и предписаниями, вы можете нажать «Отправить» для подачи апелляции, и мы обработаем ее как можно скорее.
Комментарии ( 0 )