# Работа с геттерами и сеттерами в ООП на PHP

Давайте рассмотрим следующий класс:

`<?php class User { public $name; public $age; // Метод для изменения возраста юзера: public function setAge($age) { // Проверим возраст на корректность: if ($this->isAgeCorrect($age)) { $this->age = $age; } } // Метод для проверки возраста: private function isAgeCorrect($age) { return $age >= 18 and $age <= 60; } } ?>`

Как вы видите, у нас есть публичные свойства `name` и `age`, публичный метод `setAge` для изменения возраста и приватный метод проверки возраста `isAgeCorrect`.

Очевидно, что предполагается, что возраст всегда будет меняться через метод `setAge`, так как в нем выполняется проверка возраста на корректность.

Однако, ничего не мешает сделать так:

`<?php $user = new User; // Вместо вызова setAge установим некорректный возраст напрямую: $user->age = 100500; // и у нас получится! ?>`

Упс... Получается, что мы надеемся, что везде и всегда возраст будет меняться через `setAge`, но случайно другой программист или мы сами можем напрямую обратиться к свойству и записать в него все, что угодно.

Это ошибкоопасное место и с этим нужно что-то сделать.

Для решения проблемы можно объявить возраст приватным:

`<?php class User { public $name; private $age; // объявим возраст приватным public function setAge($age) { // Проверим возраст на корректность: if ($this->isAgeCorrect($age)) { $this->age = $age; } } private function isAgeCorrect($age) { return $age >= 18 and $age <= 60; } } ?>`

Теперь установить возраст напрямую (корректный или нет - не важно) не получится:

`<?php $user = new User; // Теперь установить возраст напрямую не получится: $user->age = 100500; // увидим ошибку PHP! ?>`

Отлично, мы получили то, что хотели. Но теперь есть другая проблема: мы не можем прочитать возраст снаружи, так как он приватный:

`<?php $user = new User; // Правильным образом установим возраст: $user->setAge(50); // Попытка прочитать новый возраст приведет к ошибке PHP: echo $user->age; // а нам бы этого не хотелось... ?>`

Для решения проблемы сделаем еще один метод `getAge`, с помощью которого мы будем прочитывать значения свойства `age`:

`<?php class User { public $name; private $age; // объявим возраст приватным // Метод для чтения возраста юзера: public function getAge() { return $this->age; } public function setAge($age) { if ($this->isAgeCorrect($age)) { $this->age = $age; } } private function isAgeCorrect($age) { return $age >= 18 and $age <= 60; } } ?>`

Теперь мы свободно можем и менять, и получать возраст:

`<?php $user = new User; // Установим возраст: $user->setAge(50); // Прочитаем новый возраст: echo $user->getAge(); // выведет 50 ?>`

Такой подход, который мы сейчас сделали, - стандартный. Его удобно использовать тогда, когда нам нужна какая-то проверка в сеттере. В терминах этого подхода метод `getAge` называется геттером (англ. getter), а метод `setAge` - сеттером (англ. setter).

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

Сделайте класс `Employee`, в котором будут следующие приватные свойства: `name`, `age` и `salary`.

Сделайте геттеры и сеттеры для всех свойств класса `Employee`.

Дополните класс `Employee` приватным методом `isAgeCorrect`, который будет проверять возраст на корректность (от `1` до `100` лет). Этот метод должен использоваться в сеттере `setAge` перед установкой нового возраста (если возраст не корректный - он не должен меняться).

Пусть зарплата наших работников хранится в долларах. Сделайте так, чтобы геттер `getSalary` добавлял в конец числа с зарплатой значок доллара. Говоря другими словами в свойстве `salary` зарплата будет хранится просто числом, но геттер будет возвращать ее с долларом на конце.

←→
↑