Русский
Русский
English
Статистика
Реклама

Recovery mode ООП Кто взял Измаил? Вопрос принадлежности методов объекту

Данная статья посвящена разбору вопроса о том, какому именно объекту ООП должен принадлежать метод, осуществляющий взаимодейстие между несколькими сущностями.
Это распространённая тема для холиваров. Например:
Не используйте ООП. Никогда. Это ошибка.
На эту тему есть много материалов, к примеру: www.youtube.com/watch?v=QM1iUe6IofM

Если ООП все еще кажется вам хорошей идеей, то решите простую задачку:
Есть три объекта: кошка, кормушка и человек. Вам необходимо написать метод, который бы позволял человеку покормить кошку, воспользовавшись кормушкой.
Вопрос: методом какого класса будет являться метод.покормить()?
Просьба привести аргументированный ответ, в соответствии с иерархией классов, и другими лучшими практиками ООП.

Теперь сравните это с функциональной реализацией:
У вас есть функция покормитьКошку() принимающая в качестве аргумента ссылку на кошку и кормушку.
Цитата из холивара

Как ответить на данный вопрос?
Вначале давайте рассмотрим пример из физики.

Кейс 1 (из физики): закон Ома

Закон Ома: I=U/R, где I сила тока, U напряжение, R сопротивление.

Несложно заметить, что закон Ома, как и любую другую формулу из трех переменных, можно записать тремя способами: I=U/R, R=U/I, U=IR. Как выработать правило, позволяющее однозначно определить единственную форму записи? Очень просто: надо записать с левой стороны производную величину, т.е. ту, которая становится имеющей определённое значение, в зависимости от остальных величин.

I=U/R Сила тока СТАНОВИТСЯ равной отношению напряжения на концах проводника к сопротивлению проводника верно.

U=IR Напряжение на концах проводника СТАНОВИТСЯ равным его сопротивлению, умноженному на силу тока через проводник не верно.

R=U/I Сопротивление проводника СТАНОВИТСЯ равным отношению напряжения на концах к силе тока не верно.

Видите как только мы условились, что производное значение находится слева, остался только один вариант.

Вот так же, мы поступим и в ООП. Условимся, что метод принадлежит тому, кто воздействует:

Кто_действует.Метод(Объект_воздействия);

Кейс 2: Кто взял Измаил?


Следовательно, при ответе на вопрос Кто взял Измаил? с точки зрения объектно ориентированного программирования, и с позиции кто воздействует?, правильный ответ будет Суворов.ВзятьКрепость(Измаил, Турки):boolean. Все другие варианты, такие как: Турки.Про***тьКрепость(Измаил, Суворову), Измаил.СменаСобственника(Турки, Суворов), АбстрактнаяКрепость.БытьЗахваченной(Исмаил, Суворов, Турки) и т.д. все эти варианты не верны.

Кейс 3: Человек, кормушка и кошка

Покорми кошку! с сайта corchaosis.ru

Человек насыпал еды в кормушку. Это метод: Человек.НасыпатьЕдыКошке(ПакетЕды, Кормушка). При выполнении метода, в глобальной переменной ПакетЕды количество еды уменьшается, а в глобальной переменной Кормушка появляется.

А как же кошка? А кошка существует ДО вызова метода НасыпатьЕдыКошке, как условие его вызова. Если кошка на даче, то и метод НасыпатьЕдыКошке вызываться не будет.

Кейс 4: Игрок в DOOM, шотган и монстр

Допустим, что вопрос попадания в монстра не имеет градаций: либо попал, либо не попал.
Правильная реализация. Всё начинается с метода Игрока:

Игрок (либо, Игрок_1 в многопользовательской игре).Выстрел(Монстр_1)
Внутри реализации метода Выстрел, мы видим, что текущее оружие игрока шотган.
Следовательно, вызываем метод вложенного объекта: Игрок_1.Оружие[Игрок_1.Номер_выбранного_оружия].Выстрел(Монстр_1)

Игрок_1.Оружие это класс TWeapon.
В данном случае, вызывается метод класса TShotgun, который является дочерним к TWeapon.
Итак, имеем: Шотган.Выстрел(Монстр_1)

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

Если бы мы выстрелили из ракетницы, то появился бы новый объект ракета. Со своим методом Tick, обрабатывающим действия за один тик игрового времени (игровое время изменяется, обычно, в тиках). Но мы выстрелили из оружия, поражающего без задержки, поэтому знаем количество выстреленных патронов (1 или 2), знаем расстояние (сравнивая Игрок.Position и Монстр_1.Position), и внутри метода класса Шотган, рассчитываем ущерб.

И, наконец, Монстр_1.НанесёноПовреждение(сила_повреждения:Float). Теперь, как и перед этим шотган менял внутреннее состояние (кол-во патронов), теперь Монстр_1 меняет внутреннее состояние Монстр_1.Здоровье, и сценарий поведения (особенно, если Здоровье стало меньше нуля).

Итак, мы видим, что благодаря ООП, мы можем легко добавить новое оружие: достаточно описать его как дочерний класс от TWeapon, определить Выстрел и разместить на карте. Класс Игрок уже умеет подбирать и добавлять в свой игровой набор объекты TWeapon. Всё. Хотя нет, не всё. Если оружие будет дарить монстрам цветочки, заставляя их влюбляться в игрока, то и монстрам следует прописать метод ОтветитьНаПризнаниеВЛюбви:boolean, а также набор других методов в зависимости от степени проработки, в этом случае вам может потребоваться и ряд новых ООП объектов и их методов.

Кейс 5: Потрогать руками это функция или метод

Не только ответ на этот вопрос, но и сам интерфейс взаимодействия, очевидно, находится в зависимости от трогаемого объекта.

Потрогать_руками:: дом это функия.

Потрогать_руками:: ноутбук это метод объекта ноутбук. Вы должны использовать интерфейс, чтобы вызвать методы ноутбука KeyDown, KeyUp, KeyPressed передав в эти методы правильные данные: какая кнопка была нажата, в какой момент времени и т.д.

Потрогать_руками:: огонь это метод объекта вы. Вам необходим объект self, изменение состояние которого правильно опишет ожог руки. Огонь состояния не изменит.

Думаю, вы и сами можете продолжить список интерфейстов объектов, которые можно потрогать руками, с целью получения практики использования объектно-ориентированного программирования.
Источник: habr.com
К списку статей
Опубликовано: 19.07.2020 10:08:57
0

Сейчас читают

Комментариев (0)
Имя
Электронная почта

Анализ и проектирование систем

Ооп

Программирование

Проектирование и рефакторинг

Ооп головного мозга

Процесс разработки

Процедурное программирование

Проектирование систем

Категории

Последние комментарии

© 2006-2020, personeltest.ru