Introduction
PHP, widely known for its leniency in type declarations, has been adopting features enhancing code reliability. Optional type declarations, introduced in PHP 7, serve as instruments for cleaner, clearer, and more robust codebases.
Getting Started with Types
Type declarations, also known as type hints, allow developers to specify the expected data type of arguments in function calls, return types from functions, and class properties. Here’s a quick example:
function add(int $a, int $b): int {
return $a + $b;
}
This function mandates that both parameters must be integers, and it will return an integer as well.
Scalar Type Declarations
Scalar types were a significant addition in PHP 7. They allow functions to require parameters to be of type int, float, string, or bool. Here’s how you can use them:
function setAge(int $age) {
echo "You are {$age} years old.";
}
Strict vs. Coercive Typing
PHP 7 introduced a strict typing mode. This is enabled by declaring declare(strict_types=1);
at the top of the file, which forces PHP to adhere to the specified types otherwise it will throw a TypeError. Here’s the difference in behavior:
// Coercive mode
function addNumbers($a, $b): int {
return $a + $b;
}
addNumbers('3', 4.2); // This will work, outputting 7
// Strict mode
declare(strict_types=1);
function addNumbersStrict($a, $b): int {
return $a + $b;
}
addNumbersStrict('3', 4.2); // TypeError
In coercive mode, PHP will juggle types to match the declaration if possible, while in strict mode, it will not.
Union Types
PHP 8 brings union types, allowing a parameter or return type to accept multiple types. This is particularly useful in polymorphic scenarios:
function processInput(string|int $data) {
if (is_int($data)) {
echo "Integer received: $data";
} else {
echo "String received: $data";
}
}
Complex Types: Arrays and Objects
Beyond scalar types, PHP allows for complex type declarations such as arrays and objects. Here’s how these might be used:
function configure(array $settings) {
// Process settings array
}
class User {}
function newUser(User $user) {
// Process User object
}
Nullables and Defaults
Nullables, designated by a question mark before the type declaration, allow the parameter to be either of the specified type or null. Here’s how to employ nullables:
function setProfile(string $name, ?string $bio) {
if (is_null($bio)) {
echo "Welcome, $name!";
} else {
echo "Welcome, $name! Read their bio: $bio";
}
}
Property Type Declarations
With PHP 7.4, property type declarations were introduced, providing the ability to declare types for class and object properties. Example:
class Item {
public int $id;
public string $name;
}
Advanced: Variadics and Types
Variadic functions can also utilize type declarations, ensuring all values passed into a variable-length argument list are of the same type:
function addAll(int ...$numbers): int {
return array_sum($numbers);
}
Using Types in Anonymous Functions
Anonymous functions, also known as closures, can benefit from type declarations as follows:
$arrayOfNumbers = [1, 2, 3];
$arrayOfNumbers = array_map(
function (int $number): int {
return $number * 2;
},
$arrayOfNumbers
);
Backward Compatibility
New type declarations are generally backward compatible, but introducing them to legacy code should be done cautiously. Type errors may arise in code where informal typing was previously used.
Conclusion
Type declarations in PHP enhance the robustness and clarity of code. They introduce a layer of reinforcing the developer’s intent and making sure the code works as expected. With a number of options that scale from scalar to complex types, there’s a valuable set of tools at one’s disposal for writing clean, predictable PHP code.