Типизация данных
С каждой версией язык php обрастает новыми возможностями, делая жизнь разработчиков проще. В этой статье мы обсудим возможности типизации в современных версиях PHP и преимущества использования типов.
Типизация в PHP
В языке PHP динамическая типизация. Это значит, что при инициализации переменной ей нельзя назначить тип. Тип переменной выставиться динамически в зависимости от значения (или результат выполнения выражения), которое ей присваивается. Он может меняться в процессе выполнения скрипта:
<?php
// инициализируем переменную, присвоив ей целочисленное значение
$myVar = 15;
var_dump($myVar); // выведет int(15)
// теперь преобразуем тип в строковый
$myVar = (string)$myVar;
var_dump($myVar); // выведет string(2) "15"
// прибавим к строке число, php автоматически преобразует строковое значение к целочисленному
$myVar = $myVar + 5;
var_dump($myVar); // выведет int(20)
// добавим к числу строку, в результате чего php преобразует исходное значение в строку
$myVar = $myVar . ' яблок';
var_dump($myVar); // выведет string(13) "20 яблок"
Есть языки программирования со статической типизацией. В них при инициализации переменной нужно обязательно указывать тип. В случае, если переменной будет присваиваться значение типа, отличного от указанного, то компилятор сообщит об ошибке.
Типизация аргументов в функциях и методах
В последних версиях PHP появился возможность указывать типы для аргументов функций и возвращаемого ею значения. Рассмотрим эти возможности на примере:
<?php
// включаем строгую типизацию
declare(strict_types=1);
function myTestOperation(int $firstParam, string $secondParam, array $thirdParam) : bool
{
return true;
}
// вызываем функцию
myTestOperation(123, 'test', [4, 5, 6]);
Код содержит функцию с 3 аргументами различных типов. Типы указываются перед именем аргумента, а тип возращаемого значения после двоеточия.
Обратите внимание на строку declare(strict_types=1);
, она включает строгую типизацию. Например, если при строгой типизации мы передадим в первый аргумент функции строку вместо числа, то получим ошибку:
TypeError: Argument 1 passed to myTestOperation() must be of the type int, string given
Если удалить строчку declare(strict_types=1)
, PHP попытается преобразовать переданную строку в число. Если преобразовать невозможно, PHP выбросит исключение TypeError
.
Определение типа
Какие определения типов могут использоваться при типизации:
-
bool
допустимые значенияtrue
иfalse
-
float
значение должно число с плавающей точкой -
int
значение должно представлять целое число -
string
значение должно представлять строку -
mixed
любое значение -
callable
значение должно представлять функцию -
array
значение должно представлять массив -
iterable
значение должно представлять массив или класс, который реализует интерфейсTraversable
. Применяется при переборе в циклеforeach
-
Имя класса
объект должен представлять данный класс или его производные классы -
Имя интерфейса
объект должен представлять класс, который реализует данный интерфейс -
Self
объект должен представлять тот же класс или его производный класс. Может использоваться только внутри класса -
parent
объект должен представлять родительский класс данного класса. Может использоваться только внутри класса
Null и void в сигнатуре функции
В случае, если функция или метод класса не возвращают значение, после двоеточия пишется ключевое слово void
:
function myAction() : void
{
// в функции не должно быть return
}
В случае, если какие-то из аргументов функции мы захотим сделать необязательными, нам нужно добавить знак ?
перед именем типа.
Это правило работает и для возвращаемого значения. Например, для аргумента ?int $myVar
можно передать значение либо null
, либо целое число. Чтобы явно не передавать null
в качестве значения необязательного аргумента, обычно в сигнатуре присваивают значение по умолчанию, как показано в следующем примере:
function myTestOperation(int $firstParam, ?string $secondParam = null, ?array $thirdParam = null) : ?float
{
// выведет int(6)
var_dump($firstParam);
// выведет NULL
var_dump($secondParam);
// выведет NULL
var_dump($thirdParam);
// можно венруть null, так как в сигнатуре ?float (либо десятичная дробь, либо null)
return null;
}
// вызываем функцию, явно передаем null во 2 и 3 аргументы
myTestOperation(6, null, null);
// Вызываем еще раз, при этом не передаем необязательные аргуметы, так как в сигнатуре присвоены дефолтные значения, при этом результат выполнения будет идентичен
myTestOperation(6);
Типизация свойств объекта в PHP 7.4
В PHP версии 7.4 появилась возможность указывать типы в классах:
<?php
class MyClass
{
private string $myParamOne;
private int $myParamTwo;
private array $myParamThree;
private Object $myParamFour;
}
Преимущества указания типов в PHP
Использование типов и строгой типизации дает на следующие преимущества:
- Снижает риск ошибок, связанными с типами;
- Выполняет функцию документации — то есть мы видим: какого типа данные нужно передавать в качестве аргумента в функцию;
- Заставляет вас правильно проектировать функцию, не позволяя принимать аргументы и возвращать значения разных типов.