The Evolution of OOP in PHP: From 7.0 to 8.3
Hey there, PHP enthusiasts! 🚀 Here on the ‘Loop, we’re embarking on a time-travel adventure for this first portion of this article, exploring how Object-Oriented Programming (OOP) in PHP has evolved from version 7.0 all the way to the sleek and sophisticated 8.3. Buckle up, as we dive into the world of PHP OOP, where each version brought new superpowers to our code!
Remember when PHP 7.0 hit the scene? It was a game-changer! PHP 7 introduced us to type declarations, giving us more control over our code.
Code Sample: PHP 7.0 Type Declarations
class Spacecraft {
public function setSpeed(int $speed) {
// Set the spacecraft speed
}
}
In this snippet, the setSpeed method explicitly requires an integer. This was a big step towards making PHP scripts more robust and error-resistant.
PHP 8.0: Leveling Up
Fast forward to PHP 8.0, and things got even more exciting! With features like union types, constructor property promotion, and attributes, our OOP practices leveled up.
Code Sample: PHP 8.0 Union Types and Constructor Promotion
class Astronaut {
public function __construct(
public string|int $id,
public readonly string $name
) {}
}
Here, an astronaut’s id can be both a string or an int, thanks to union types. Plus, constructor property promotion made our code neater!
PHP 8.3: The Modern PHP
Now, we’ve reached PHP 8.3, where OOP shines brighter than ever. With readonly classes, new array functions, and other cool features, PHP’s OOP is more powerful and flexible.
Code Sample: Readonly Classes in PHP 8.3
readonly class Planet {
public function __construct(
public readonly string $name
) {}
}
With PHP 8.3, Planet is a readonly class, ensuring immutability and data integrity.
This journey from PHP 7.0 to 8.3 shows how PHP has continuously improved, making our OOP experience better and more efficient. Stay tuned as we explore each of these features in more detail!
This introduction sets the stage for our deep dive into the OOP enhancements across these PHP versions
Class Design Principles in Modern PHP
Moving into the heart of OOP with PHP 8.3, let’s focus on class design principles – the backbone of effective and efficient object-oriented programming. In this part, we’re going to unravel the best practices for designing classes in PHP, ensuring they are reusable, maintainable, and robust.
1. Single Responsibility Principle (SRP)
Each class should have one responsibility, one reason to change. This keeps your classes clean and focused.
/**
* Class responsible for planning space missions. (and only missions)
*/
class SpaceMissionPlanner {
/**
* Constructor for SpaceMissionPlanner.
*
* @param array $missionData Data related to the space mission.
*/
public function __construct(private array $missionData) {}
/**
* Creates a timeline for the space mission.
*/
public function createMissionTimeline() {
// Logic to create mission timeline
}
/**
* Assigns astronauts to the space mission.
*/
public function assignAstronauts() {
// Logic to assign astronauts to the mission
}
// Other mission planning methods...
}
2. Open/Closed Principle
Classes should be open for extension but closed for modification. This encourages enhancing classes without changing existing code.
abstract class SpaceVehicle {
abstract public function launch();
}
class Rocket extends SpaceVehicle {
public function launch() {
// Launch logic for a rocket
}
}
class Shuttle extends SpaceVehicle {
public function launch() {
// Launch logic for a shuttle
}
}
3. Liskov Substitution Principle
Derived classes must be substitutable for their base classes, ensuring consistency and reliability in class hierarchies.
class CargoModule {
public function loadCargo() {
// Load cargo
}
}
class ScienceModule extends CargoModule {
public function loadCargo() {
// Additional steps for scientific equipment
}
}
4. Interface Segregation
Use specific interfaces rather than one general-purpose interface, providing flexibility and modularity.
interface NavigationSystem {
public function navigate();
}
interface CommunicationSystem {
public function transmit();
}
class SpaceProbe implements NavigationSystem, CommunicationSystem {
public function navigate() {
// Navigation logic
}
public function transmit() {
// Transmission logic
}
}
5. Dependency Inversion
High-level modules should not depend on low-level modules. Both should depend on abstractions.
interface MissionCommand {
public function executeCommand();
}
class ExplorationMission implements MissionCommand {
public function executeCommand() {
// Exploration logic
}
}
/**
* Class for controlling space missions.
*/
class MissionControl {
/**
* Constructor for MissionControl.
*
* @param MissionCommand $mission The mission command interface.
*/
public function __construct(private MissionCommand $mission) {}
/**
* Initiates the space mission.
*/
public function initiateMission() {
$this->mission->executeCommand();
}
}
These principles will guide you to create classes that are easy to manage, test, and scale, fitting perfectly into the modern PHP ecosystem!
Keep reading further as we delve deeper into these principles with more examples and explore how PHP 8.3’s features align with and enhance these OOP best practices!
/**
* Trait for logging messages.
*/
trait Loggable
{
public function log(string $message){
echo $message . "\n";
}
}
/**
* Interface for navigable vehicles.
*/
interface Navigable
{
public function navigate(): void;
}
/**
* Base class for space vehicles.
*/
class SpaceVehicle
{
use Loggable;
/**
* Constructs a space vehicle.
*
* @param int $fuel Initial fuel amount.
*/
public function __construct(private int $fuel){
}
/**
* Refuels the vehicle.
*
* @param int $amount Amount of fuel to add.
*/
public function refuel(int $amount): void{
$this->fuel += $amount;
$this->log("Vehicle refueled with $amount units.");
}
}
/**
* Rocket class implementing Navigable.
*/
class Rocket extends SpaceVehicle implements Navigable
{
/**
* Navigates the rocket.
*/
public function navigate(): void{
if($this->fuel > 0){
$this->log("Rocket navigating to destination.");
}else{
$this->log("Cannot navigate, out of fuel!");
}
}
/**
* Launches the rocket.
*/
public function launch(): void{
if($this->fuel > 0){
$this->log("Rocket launching with fuel level: $this->fuel");
}else{
$this->log("Rocket cannot launch due to no fuel.");
}
}
}
// Utilization
$missionRocket = new Rocket(50);
$missionRocket->launch();
$missionRocket->navigate();
In this example:
Loggabletrait is used for logging messages.SpaceVehicleis a base class with a refueling capability.RocketextendsSpaceVehicleand implementsNavigable, showcasing inheritance and interface implementation.
This code effectively demonstrates how traits, interfaces, and inheritance can be combined to create a flexible and modular OOP design in PHP!
Let’s take off! 🚀🪐

Leave a Reply