The following text is a partial translation of the original English article, performed by ChatGPT (gpt-3.5-turbo) and this Jekyll plugin:
Объекты, отвечающие за слишком много вещей, представляют проблему. Из-за их высокой сложности они трудны в поддержке и расширении. Декомпозиция ответственности - это то, что мы делаем, чтобы разбить эти чрезмерно сложные объекты на более мелкие. Я вижу два типа этой операции рефакторинга: вертикальную и горизонтальную. И я считаю, что первая лучше второй.
Допустим, это наш код (он написан на Ruby):
Очевидно, объекты этого класса делают слишком много. Они сохраняют строки журнала в файл и также форматируют их - это очевидное нарушение знаменитого принципа единственной ответственности. Объект этого класса будет ответственным за слишком много вещей. Нам нужно извлечь некоторую функциональность из него и поместить ее в другой объект(ы). Нам нужно декомпозировать его ответственность. Независимо от того, где мы его разместим, так будет выглядеть класс Log
после извлечения:
Теперь он только сохраняет строки в файле, что идеально. Класс является связанным и небольшим. Давайте создадим экземпляр этого класса:
Далее, куда мы ставим строки с функциональностью форматирования, которые только что были извлечены? Есть два подхода к разделению ответственности: горизонтальный и вертикальный. Этот подход является горизонтальным:
Чтобы использовать Log
и Line
вместе, мы должны сделать следующее:
Видите, почему это горизонтально? Потому что этот скрипт видит оба объекта. Они оба находятся на одном уровне видимости. Мы всегда должны общаться с обоими объектами, когда хотим записать строку. Оба объекта Log
и Line
находятся перед нами. Чтобы записать строку, нам придется иметь дело с двумя классами:
[скрипт] -вниз-> [лог] [скрипт] -вниз-> [строка]
Наоборот, эта декомпозиция ответственности является вертикальной:
Класс TimedLog
является декоратором, и вот как мы их используем вместе:
Теперь мы просто добавляем строку в журнал:
Ответственность разложена по вертикали. У нас все еще есть одна точка входа в объект log
, но объект «состоит» из двух объектов, один из которых обернут в другой:
[script] -down-> [TimedLog] [TimedLog] -down-> [Log]
В общем, я считаю, что горизонтальное разложение ответственности - плохая идея, в то время как вертикальное разложение гораздо лучше. Это потому, что вертикально разложенный объект уменьшает сложность, в то время как горизонтально разложенный объект на самом деле делает вещи более сложными, потому что его клиентам приходится иметь дело с большим количеством зависимостей и точек контакта.
Translated by ChatGPT gpt-3.5-turbo/42 on 2023-11-17 at 14:40