Зарегистрируйтесь для доступа к 15+ бесплатным курсам по программированию с тренажером

Изменяемость PHP: Введение в ООП

Сеттеры (setters) служат для изменения внутреннего состояния объекта. Как и геттеры, они именуются особым образом. К сеттерам обычно добавляется префикс set, если этот сеттер что-то устанавливает и add — если добавляет.

<?php

$point1 = new Point(10, 11);
$point2 = new Point(-3, 3);
$segment = new Segment($point1, $point2);

$segment->getStartPoint(); // (10, 11)
$segment->setStartPoint(new Point(3, 8)); // Допустимо, потому что new Point(3, 8) — выражение
$segment->getStartPoint(); // (3, 8)

На практике изменения объектов происходят почти всегда с помощью сеттеров, и крайне редко — через изменение свойства напрямую. Причём объекты (впрочем, как и любая абстракция) иногда хранят внутри себя свойства, которые нельзя изменять снаружи (например, соединение с базой данных), и для них не делают сеттеров.

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

Например, ранее мы создали класс для работы с рациональными числами. Если бы методы add() и sub() изменяли объект, на котором вызываются, то получить неверные расчёты стало бы крайне просто. Достаточно использовать одно рациональное число в нескольких местах, и любое его изменение повлияет на всех, кто использует это число. Абсолютно такая же ситуация и с графическими примитивами на плоскости.

<?php

$point1 = new Point(10, 11);
$point2 = new Point(-3, 3);
$segment1 = new Segment($point1, $point2);
$segment2 = new Segment($point2, $point1);

// Функция moveUp перемещает весь отрезок на три значения вверх.
// Она не возвращает новый отрезок, а изменяет сам объект.
$segment1->moveUp(3);
print_r($segment1); // => [(10, 14), (-3, 6)]

Если внутри moveUp() происходит изменение точек (вместо создания новых), то такое изменение повлияет и на segment2, хотя мы и не собирались его перемещать.

<?php

// Такое поведение неожиданно
// Сегмент изменился, хотя напрямую его никто не менял
print_r($segment2); // => [(-3, 6), (10, 14)]

Существует ли способ сделать всё красиво? Нет, фундаментальная проблема "изменяемое состояние" может быть убрана только отказом от изменения и созданием нового на основе старого. Последний приём подходит не всегда, но мы уже использовали его на практике, например, в рациональных числах.


Аватары экспертов Хекслета

Остались вопросы? Задайте их в разделе «Обсуждение»

Вам ответят команда поддержки Хекслета или другие студенты.

Ошибки, сложный материал, вопросы >
Нашли опечатку или неточность?

Выделите текст, нажмите ctrl + enter и отправьте его нам. В течение нескольких дней мы исправим ошибку или улучшим формулировку.

Что-то не получается или материал кажется сложным?

Загляните в раздел «Обсуждение»:

  • задайте вопрос. Вы быстрее справитесь с трудностями и прокачаете навык постановки правильных вопросов, что пригодится и в учёбе, и в работе программистом;
  • расскажите о своих впечатлениях. Если курс слишком сложный, подробный отзыв поможет нам сделать его лучше;
  • изучите вопросы других учеников и ответы на них. Это база знаний, которой можно и нужно пользоваться.
Об обучении на Хекслете

Для полного доступа к курсу нужна профессиональная подписка

Профессиональная подписка откроет полный доступ ко всем курсам, упражнениям и урокам Хекслета, проектам и пожизненный доступ к теории пройденных уроков. Подписку можно отменить в любой момент.

Получить доступ
900
упражнений
2000+
часов теории
3200
тестов

Открыть доступ

Курсы программирования для новичков и опытных разработчиков. Начните обучение бесплатно.

  • 120 курсов, 2000+ часов теории
  • 900 практических заданий в браузере
  • 360 000 студентов
Отправляя форму, вы соглашаетесь c «Политикой конфиденциальности» и «Условиями оказания услуг»

Наши выпускники работают в компаниях:

Логотип компании Альфа Банк
Логотип компании Aviasales
Логотип компании Yandex
Логотип компании Tinkoff
Рекомендуемые программы

С нуля до разработчика. Возвращаем деньги, если не удалось найти работу.

Иконка программы PHP-разработчик
Профессия
Разработка веб-приложений на Laravel
29 сентября 8 месяцев

Есть вопрос или хотите участвовать в обсуждении?

Зарегистрируйтесь или войдите в свой аккаунт

Отправляя форму, вы соглашаетесь c «Политикой конфиденциальности» и «Условиями оказания услуг»