smsc banner 468x60smsc banner 728x90smsc banner 930x180etxt banner 468x60etxt banner 728x90etxt banner 930x180jivo banner 468x60jivo banner 728x90jivo banner 930x180

Руководство по ООП в PHP: классы и объекты

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

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

  • Он обеспечивает четкую модульную структуру программ.
  • Это помогает вам придерживаться принципа «не повторяйся» (DRY) и, таким образом, значительно упрощает поддержку, изменение и отладку кода.
  • Это позволяет создавать более сложное поведение с меньшим количеством кода, меньшим временем разработки и высокой степенью повторного использования.

В этом разделе будет описано, как классы и объекты работают в PHP.

Идея, лежащая в основе принципа «Не повторяйся» (DRY), состоит в том, чтобы уменьшить повторение кода за счет абстрагирования кода, который является общим для приложения, и размещения его в одном месте и повторного использования вместо его повторения.

Понимание классов и объектов

Классы и объекты — это два основных аспекта объектно-ориентированного программирования. Класс — это автономный, независимый набор переменных и функций, которые работают вместе для выполнения одной или нескольких конкретных задач, в то время как объекты являются отдельными экземплярами класса.

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

Например, представим класс как проект дома. Сам чертеж — это не дом, а подробный план дома. А объект похож на настоящий дом, построенный по этому проекту. Мы можем построить несколько одинаковых домов по одному и тому же проекту, но у каждого дома может быть разная окраска, интерьер и семья, как показано на рисунке ниже.

Класс можно объявить с помощью ключевого слова class, за которым следует имя класса и пара фигурных скобок ({}), как показано в следующем примере.

Давайте создадим PHP-файл с именем rectangle.php и поместим в него следующий пример кода, чтобы код нашего класса был отделен от остальной части программы. Затем мы можем использовать его везде, где это необходимо, просто включив файл rectangle.php.

<?php
class Rectangle
{
    // Объявляем свойства
    public $length = 0;
    public $width = 0;
    
    // Функция для получения периметра
    public function getPerimeter(){
        return (2 * ($this->length + $this->width));
    }
    
    // Функция для получения площади
    public function getArea(){
        return ($this->length * $this->width);
    }
}
?>

Ключевое слово public перед свойствами и методами в приведенном выше примере является модификатором доступа, который указывает, что это свойство или метод доступен из любого места. Мы узнаем об этом больше немного позже в этой главе.

Синтаксически переменные внутри класса называются свойствами, а функции — методами. Также имена классов обычно записываются в PascalCase, т.е. каждое объединенное слово начинается с заглавной буквы (например, MyClass).

После определения класса объекты могут быть созданы из класса с помощью ключевого слова new. Доступ к методам и свойствам класса можно получить напрямую через этот экземпляр объекта.

Создайте еще один PHP-файл с именем test.php и поместите в него следующий код.

<?php
// Включаем определение класса
require "Rectangle.php";
 
// Создаем новый объект из класса Rectangle
$obj = new Rectangle;
 
// Получаем значения свойств объекта
echo $obj->length; // Выводит: 0
echo $obj->width; // Выводит: 0
 
// Устанавливаем значения свойств объекта
$obj->length = 30;
$obj->width = 20;
 
// Читаем значения свойств объекта еще раз, чтобы показать изменение
echo $obj->length; // Выводит: 30
echo $obj->width; // Выводит: 20
 
 
// Вызываем методы объекта
echo $obj->getPerimeter(); // Выводит: 100
echo $obj->getArea(); // Выводит: 600
?>

Символ стрелки (->) — это конструкция ООП, которая используется для доступа к содержащимся в ней свойствам и методам данного объекта. Псевдопеременная $this предоставляет ссылку на вызывающий объект, то есть объект, которому принадлежит метод.

Настоящая мощь объектно-ориентированного программирования становится очевидной при использовании нескольких экземпляров одного и того же класса, как показано в следующем примере:

<?php
// Включвем определение класса
require "Rectangle.php";
 
// Создаем несколько объектов из класса Rectangle
$obj1 = new Rectangle;
$obj2 = new Rectangle;
 
// Вызываем методы обоих объектов
echo $obj1->getArea(); // Выводит: 0
echo $obj2->getArea(); // Выводит: 0
 
// Устанавливаем значения свойств $obj1
$obj1->length = 30;
$obj1->width = 20;
 
// Устанавливаем значения свойств $obj2
$obj2->length = 35;
$obj2->width = 50;
 
// Снова вызываем методы обоих объектов
echo $obj1->getArea(); // Выводит: 600
echo $obj2->getArea(); // Выводит: 1750
?>

Как вы можете видеть в приведенном выше примере, вызов метода getArea() для разных объектов заставляет этот метод работать с разным набором данных. Каждый экземпляр объекта полностью независим, со своими собственными свойствами и методами, и поэтому ими можно управлять независимо, даже если они принадлежат к одному классу.

Использование конструкторов и деструкторов

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

Например, магический метод __construct() (конструктор) выполняется автоматически всякий раз, когда создается новый объект. Точно так же магический метод __destruct() (деструктор) выполняется автоматически при уничтожении объекта. Функция деструктора очищает все ресурсы, выделенные объекту, после его уничтожения.

<?php
class MyClass
{
    // Конструктор
    public function __construct(){
        echo 'The class "' . __CLASS__ . '" was initiated!<br>';
    }
    
    // Деструктор
    public function __destruct(){
        echo 'The class "' . __CLASS__ . '" was destroyed.<br>';
    }
}
 
// Создаем новый объект
$obj = new MyClass;
 
// Выводим сообщение в конце файла
echo "The end of the file is reached.";

/* Выводит: The class "MyClass" was initiated!
The end of the file is reached.
The class "MyClass" was destroyed. */
?>

Деструктор вызывается автоматически при завершении скрипта. Однако для явного запуска деструктора вы можете уничтожить объект с помощью PHP-функции unset(), как показано ниже:

<?php
class MyClass
{
    // Конструктор
    public function __construct(){
        echo 'The class "' . __CLASS__ . '" was initiated!<br>';
    }
    
    // Деструктор
    public function __destruct(){
    echo 'The class "' . __CLASS__ . '" was destroyed.<br>';
    }
}
 
// Создаем новый объект
$obj = new MyClass;
 
// Уничтожаем объект
unset($obj);
 
// Выводим сообщение в конце файла
echo "The end of the file is reached.";

/* Выводит: The class "MyClass" was initiated!
The class "MyClass" was destroyed.
The end of the file is reached. */
?>

__CLASS__ — это магическая константа, которая содержит имя класса, в котором она встречается. Пустая, если вызывается вне класса.

Расширение классов посредством наследования

Классы могут наследовать свойства и методы другого класса с помощью ключевого слова extends. Этот процесс расширяемости называется наследованием. Это, вероятно, самая веская причина использования объектно-ориентированной модели программирования.

<?php
// Включаем определение класса
require "Rectangle.php";
 
// Определяем новый класс на основе существующего класса
class Square extends Rectangle
{   
    // Метод проверки, является ли прямоугольник также квадратом
    public function isSquare(){
        if($this->length == $this->width){
            return true; // Квадрат
        } else{
            return false; // Не квадрат
        }
    }
}
 
// Создаем новый объект из класса Square
$obj = new Square;
 
// Устанавливаем значения свойств объекта
$obj->length = 20;
$obj->width = 20;
 
// Вызываем методы объекта
if($obj->isSquare()){
    echo "The area of the square is ";
} else{
    echo "The area of the rectangle is ";
};
echo $obj->getArea(); // Выводит: The area of the square is 400
?>

Как вы можете видеть в приведенном выше примере, хотя определение класса Square явно не содержит ни метод getArea(), ни свойства $length и $width, экземпляры класса Square могут использовать их, поскольку они унаследованы от родительского класса Rectangle.

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

Управление видимостью свойств и методов

При работе с классами вы даже можете ограничить доступ к его свойствам и методам, используя ключевые слова видимости для большего контроля. Существует три ключевых слова видимости (от наиболее заметного до наименее заметного): public, protected, private, которые определяют, как и откуда можно получить доступ к свойствам и методам для их изменения.

  • public — доступ к общедоступному свойству или методу можно получить где угодно, как внутри класса, так и за его пределами. Это видимость установлена по умолчанию для всех классов в PHP;
  • protected — доступ к защищенному свойству или методу можно получить только внутри самого класса, в дочерних или унаследованных классах, то есть классах, расширяющих этот класс;
  • private — частное свойство или метод доступны только из класса, который его определяет. Даже дочерние или унаследованные классы не могут получить доступ к частным свойствам или методам.

Следующий пример покажет вам, как на самом деле работает эта видимость:

<?php
// Определяем класс
class Automobile
{
    // Объявляем свойства
    public $fuel;
    protected $engine;
    private $transmission;
}
class Car extends Automobile
{
    // Конструктор
    public function __construct(){
        echo 'The class "' . __CLASS__ . '" was initiated!<br>';
    }
}
 
// Создаем объект из класса Automobile
$automobile = new Automobile;
 
// Попытка установить свойства объекта $cars
$automobile->fuel = 'Petrol'; // ok
$automobile->engine = '1500 cc'; // fatal error
$automobile->transmission = 'Manual'; // fatal error
 
// Создаем объект из класса Car
$car = new Car;
 
// Попытка установить свойства объекта $car
$car->fuel = 'Diesel'; // ok
$car->engine = '2200 cc'; // fatal error
$car->transmission = 'Automatic'; // undefined
?>

Статические свойства и методы

В дополнение к видимости свойства и методы также могут быть объявлены как static, что делает их доступными без создания экземпляра класса. Доступ к статическим свойствам и методам можно получить с помощью оператора разрешения области видимости (::), например: ClassName::$property и ClassName::method().

К свойству, объявленному как static, нельзя получить доступ через объект этого класса, хотя можно использовать статический метод, как показано в следующем примере:

<?php
// Определяем класс
class HelloClass
{
    // Объявляем статическое свойство
    public static $greeting = "Hello World!";
    
    // Объявляем статический метод
    public static function sayHello(){
        echo self::$greeting;
    }
}
// Попытка получить доступ к статическому свойству и методу напрямую
echo HelloClass::$greeting; // Выводит: Hello World!
HelloClass::sayHello(); // Выводит: Hello World!
 
// Попытка получить доступ к статическому свойству и методу через объект
$hello = new HelloClass;
echo $hello->greeting; // Strict Warning
$hello->sayHello(); // Выводит: Hello World!
?>

Ключевое слово self в приведенном выше примере означает «текущий класс». Ему никогда не предшествует знак доллара ($), а за ним всегда следует оператор :: (например, self::$name).

Ключевое слово self отличается от ключевого слова this, которое означает «текущий объект» или «текущий экземпляр класса». Ключевому слову this всегда предшествует знак доллара ($), за которым следует оператор -> (например, $this->name).

Поскольку статические методы могут быть вызваны без экземпляра класса (то есть объекта), псевдопеременная $this недоступна внутри метода, объявленного как static.

jivo banner 480x320jivo banner 728x90jivo banner 120x600kwork banner 480x320kwork banner 728x90kwork banner 120x600etxt banner 480x320etxt banner 728x90etxt banner 120x600

Насколько публикация полезна?

Нажмите на звезду, чтобы оценить!

Средняя оценка 4.9 / 5. Количество оценок: 7

Оценок пока нет. Поставьте оценку первым.

Похожие посты

Руководство по загрузке файлов на сервер в PHP

В этом руководстве мы узнаем, как загружать файлы на удаленный сервер с помощью простой HTML-формы и PHP. Вы можете загружать файлы любого типа, например изображения, видео, ZIP-файлы, документы Microsoft Office, PDF-файлы, а также исполняемые файлы и множество других типов файлов. Шаг 1. Создание HTML-формы для загрузки файла В следующем примере будет создана простая HTML-форма, которую…
Подробнее

Руководство по GET и POST запросам в PHP

Веб-браузер связывается с сервером, как правило, с помощью одного из двух HTTP-методов (протокола передачи гипертекста) — GET и POST. Оба метода передают информацию по-разному и имеют разные преимущества и недостатки, как описано ниже. PHP-метод GET В методе GET данные отправляются в виде параметров URL, которые обычно представляют собой строки пар имени и значения, разделенные амперсандами…
Подробнее

Список сообщений об ошибках в PHP

Обычно, когда движок PHP сталкивается с проблемой, препятствующей правильной работе скрипта, он генерирует сообщение об ошибке. Существует шестнадцать различных уровней ошибок, и каждый уровень представлен целым числом и связанной с ним константой. Вот список уровней ошибок: Название Значение Описание E_ERROR 1 Неустранимая ошибка времени выполнения от которой невозможно избавиться. Выполнение скрипта немедленно прекращается E_WARNING 2…
Подробнее