Вопрос о дизайне: набирает ли телефон PhoneNumber или PhoneNumber набирает себя на телефоне? - PullRequest
8 голосов
/ 16 сентября 2008

Это переиздано из того, что я выложил на DDD Yahoo! группа.

При прочих равных вы пишете phone.dial (phoneNumber) или phoneNumber.dialOn (phone)? Имейте в виду возможные будущие требования (номера счетов в дополнение к номерам телефонов, калькуляторы в дополнение к телефонам).

Этот выбор иллюстрирует, как идиомы Информационного эксперта, Принципа единой ответственности и «Не спрашивай» противоречат друг другу.

phoneNumber.dialOn (phone) поддерживает информационный эксперт и «Не спрашивай», а phone.dial (phoneNumber) поддерживает принцип единой ответственности.

Если вы знакомы с работой Кена Пью в Prefactoring, то это Загадка электронной таблицы ; Вы добавляете строки или столбцы?

Ответы [ 13 ]

18 голосов
/ 16 сентября 2008

phone.dial(), потому что это телефон, который набирает номер.

Actor.Verb (входы) -> выходы.

9 голосов
/ 16 сентября 2008

Meh - User.Dial (номер). Телефон не имеет смысла в данном контексте. SOL (говорите вслух) - хороший способ обдумать это (помимо идиом и принципов)

Телефоны имеют циферблат. Они не могут набрать себя. Номера телефонов являются цифрами. Пользователи набирают номера телефонов на наборе номера телефона.

3 голосов
/ 16 сентября 2008

вопрос принимает контекст ответа и, следовательно, создает ложную дилемму

«загадка электронной таблицы» в данном примере является ложной дихотомией: строки и столбцы являются уровнем представления, а не обязательно уровнем данных. Комментарии ниже говорят мне, что я неправильно понял аналогию, но я так не думаю - говоря «если это строка или столбец, который с большей вероятностью изменится», вынуждает делать ненужный выбор в проблемном пространстве - они оба с одинаковой вероятностью может измениться. И в этом конкретном примере это приводит к выбору неправильной [да неправильной ] парадигмы для решения. Набор номера телефона - это то, как старые механические устройства инициировали соединение с другим старым механическим устройством; это вряд ли удачная аналогия для современной телефонии. И если предположить, что есть «пользователь», который инициирует вызов, просто перемещает проблему - хотя он перемещает ее в правильном направлении, то есть от модели телефона с поворотным механизмом; -)

Если вы посмотрите, как работает протокол TAPI [извините за опечатку ранее, это протокол TAPI, а не ATAPI!], То есть контроллер вызовов - эквивалент «пользователя», который, я полагаю, в некотором смысле - который управляет соединениями между устройствами. , Одно устройство не вызывает другое, контроллер вызовов подключает устройства. Таким образом, приведенный ниже пример по-прежнему верен. Возможно, было бы правильнее использовать объект CallController вместо общего соединения, но аналогия должна быть достаточно ясной.

В этом примере телефон - это устройство с адресом, называемым «номер телефона». Оператор «dial» устанавливает соединение между двумя устройствами. Итак, ответ:

Phone p1 = new Phone(phoneNumber1);
Phone p2 = new Phone(phoneNumber2);
Connection conn = new Connection(p1,p2);
conn.Open();
//...talk
conn.Close();

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

Connection confCall = new Connection(p1,p2,p3,p4,p5,p6);
confCall.Open();

Connection joinCall = new Connection(confCall,p7,p8,conn);
joinCall.Open();

посмотрите на протокол TAPI для большего количества примеров

1 голос
/ 17 сентября 2008

Выбор типа столбца или объекта строки для метода набора не меняет масштаб программы.

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

Если последовательность методов строк не зависит от точного знания того, какой объект столбца задействован (но зависит от того, какой конкретный объект строки задействован) и наоборот для последовательности методов столбца, то проблема масштабируется как m + n (m = количество строк, n = количество строк). Когда вы создаете новую строку, она фактически не спасает вас от работы, если для метода столбца был назначен метод dial. Вы все еще должны указать уникальную последовательность методов строк для использования в 'dial' где-нибудь!

Если, однако, скажем, что последовательность методов столбца внутри 'dial' даже не зависит от того, какой объект column задействован (они используют одну 'универсальную' последовательность методов столбца), то проблема просто масштабируется как м. На самом деле не имеет значения, если вы назначили метод «dial» для объектов столбца, программа по-прежнему масштабируется как m; по существу, не требуется никакой работы для создания нового метода набора номера при добавлении еще одного объекта столбца, и у вас явно есть возможность абстрагировать все эти методы набора в один общий метод набора номера.

1 голос
/ 17 сентября 2008

A: phone.dial (номер телефона)

PhoneNumber тупой и является только набором данных. Когда происходит "набор номера", должен ли объект PhoneNumber знать, как набирать номер? Есть много состояний для отслеживания, например:

  • Телефон уже на другом вызове? (если да / нет, что делать?)
  • Что произойдет, если метод набора изменится? (глобальный роуминг, другой оператор и т. д.)
  • А как насчет сферы? При совершении вызова необходимо добавить номер телефона в список последних исходящих вызовов.

Если ваш объект PhoneNumber должен знать все это, это не СУХОЙ и ваш код будет меньше портативный и с большей вероятностью сломается.

Я бы сказал, что у Стивена А. Лоу это есть. Это должно быть сделано с помощью объекта типа Controller для обработки различных состояний и т. Д. Держите объект PhoneNumber в тупом состоянии и передавайте умения посреднику, которому нужно беспокоиться о том, чтобы телефон гудел.

1 голос
/ 16 сентября 2008

Ни. Пользователь набирает номер телефона на телефоне.

1 голос
/ 16 сентября 2008

Очевидно, что интерфейс PhoneUserInterface, реализацию которого вы можете получить из метода PhoneUserFactory.CreatePhoneUser (), имеет метод dial (Phone, Number), который можно использовать для набора номера телефона.

РЕДАКТИРОВАТЬ: Ответ на комментарий. Ни. На телефоне должна быть кнопка Pressed () или что-то в этом роде. Пользователь вводит цифры / символы телефонного номера через этот интерфейс.

1 голос
/ 16 сентября 2008

Понятно, тел. Набор (номер)

1 голос
/ 16 сентября 2008

Если вы пишете OO, тогда вы начинаете с базового объекта, который не является номером, номер идет в телефон, поэтому phone.dial () таким образом вы также можете phone.answer () phone.disconnect () phone.powerOFF и т. д.

Другой способ взглянуть на это - набирает ли номер телефон или набирает номер?

0 голосов
/ 16 сентября 2008

У меня вообще не было бы номера телефона как класса, так как он не имеет никакого поведения, это просто элемент данных.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...