Skip to main content

Polymorphism

Polymorphism is one of the Four Pillars of Object Oriented Programming.

The word comes from Greek:

Poly = Many
Morph = Forms

Meaning:

One thing can exist in many forms.

What is Polymorphism?

Polymorphism allows different classes to be treated as the same type.

Example:

Player
Zombie
Cow
Skeleton

All are:

Entity

This allows us to write code like:

function process(
Entity $entity
) {

}

The function can now accept:

  • Player
  • Zombie
  • Cow
  • ItemEntity

All without rewriting code.


Why Polymorphism Exists

Without polymorphism:

processPlayer();

processZombie();

processCow();

processSkeleton();

Huge duplication.


With polymorphism:

process(
Entity $entity
);

Everything becomes simpler.


Real Life Example

Think about:

Remote Control

Pressing:

Power Button

works for:

  • TV
  • AC
  • Fan
  • Speaker

Same action.

Different behavior.

This is polymorphism.


First Example

Parent:

class Animal {

public function sound() {

echo "Unknown";

}

}

Child:

class Dog
extends Animal {

public function sound() {

echo "Bark";

}

}

Another Child:

class Cat
extends Animal {

public function sound() {

echo "Meow";

}

}

Usage:

$animals = [

new Dog(),
new Cat()

];

foreach ($animals as $animal) {

$animal->sound();

}

Output:

Bark
Meow

Same Method

sound()

Different behavior.

This is:

Runtime Polymorphism

Visualization

Animal

├── Dog → Bark
├── Cat → Meow
└── Bird → Tweet

Method Overriding

Polymorphism usually works through:

Method Overriding

Parent:

class Animal {

public function move() {

echo "Moving";

}

}

Child:

class Bird
extends Animal {

public function move() {

echo "Flying";

}

}

Child:

class Fish
extends Animal {

public function move() {

echo "Swimming";

}

}

Parent References

Example:

$animal =
new Dog();

This is valid.

Why?

Because:

Dog IS AN Animal

Visualization

Animal


Dog

Dynamic Dispatch

Example:

$animal =
new Dog();

$animal->sound();

Output:

Bark

PHP automatically chooses:

Dog::sound()

instead of:

Animal::sound()

This is called:

Dynamic Dispatch

Polymorphic Functions

Example:

function makeSound(
Animal $animal
) {

$animal->sound();

}

Usage:

makeSound(
new Dog()
);

makeSound(
new Cat()
);

Output:

Bark
Meow

Why This is Powerful

One function.

Unlimited object types.


PocketMine Example

Simplified:

function attack(
Entity $entity
) {

}

Can receive:

Player
Zombie
Cow
Villager

Entity Hierarchy

Entity

├── Human
│ └── Player

├── Monster
│ ├── Zombie
│ └── Skeleton

└── Animal

Real Example

foreach (
$world->getEntities()
as $entity
) {

$entity->setNameTag(
"Hello"
);

}

Every entity receives same method call.

Polymorphism.


instanceof

Sometimes behavior differs.

Example:

if (
$entity instanceof Player
) {

$entity->sendMessage(
"Hello"
);

}

Another:

if (
$entity instanceof Zombie
) {

$entity->setHealth(
100
);

}

Visualization

Entity

instanceof

Player ?
Zombie ?
Cow ?

Interfaces and Polymorphism

Polymorphism becomes even more powerful with interfaces.

Example:

interface Logger {

public function log(
string $message
);

}

Implementations:

class FileLogger
implements Logger {

}
class DiscordLogger
implements Logger {

}

Usage:

function write(
Logger $logger
) {

}

Can accept:

FileLogger
DiscordLogger
DatabaseLogger

Real World Example

Payment System:

PaymentMethod

├── PayPal
├── Stripe
└── Crypto

Function:

pay(
PaymentMethod $method
);

Unlimited payment systems.


Another Example

Notification System:

Notifier

├── EmailNotifier
├── DiscordNotifier
└── SmsNotifier

Enterprise Example

interface Cache {

}

Implementations:

Redis
Memcached
FileCache

Everything works together.


Polymorphism in Laravel

Laravel internally uses:

Cache Driver
Queue Driver
Mail Driver
Database Driver

All are polymorphic.


Real PocketMine Examples


Commands

Command

├── BanCommand
├── KickCommand
└── WarpCommand

Events

Event

├── PlayerJoinEvent
├── BlockBreakEvent
└── EntityDamageEvent

Entities

Entity

├── Player
├── Zombie
└── Cow

Benefits


1. Less Duplication

One function.

Many object types.


2. Better Extensibility

Add new classes without modifying old code.


3. Cleaner Architecture

Projects remain organized.


4. Easier Maintenance

No giant if statements.


Example

Bad:

if ($type === "dog") {

}

if ($type === "cat") {

}

Good:

$animal->sound();

Open Closed Principle

Polymorphism helps follow:

Open for Extension
Closed for Modification

Add new classes.

No existing code changes.


Common Beginner Mistakes


Giant If Statements

Bad:

if ($animal === "dog")

Use polymorphism.


Excessive instanceof

Sometimes acceptable.

But too much means bad design.


Breaking Inheritance

Methods should maintain behavior contracts.


Best Practices

✅ Prefer interfaces.

✅ Prefer polymorphism over condition chains.

✅ Use inheritance carefully.

✅ Keep common behavior in parent classes.


Exercises


Exercise 1

Create:

Animal

├── Dog
├── Cat
└── Bird

Each should override:

sound()

Exercise 2

Create:

Shape

├── Circle
├── Square
└── Rectangle

Method:

area()

Exercise 3

Create:

PaymentMethod

├── PayPal
├── Crypto
└── Stripe

Method:

pay()

Mini Project

Create:

Entity

├── Player
├── Zombie
├── Skeleton
└── Cow

Method:

attack()

Each entity behaves differently.


Quiz

What does polymorphism mean?

Answer

One thing existing in many forms.


Which concept makes polymorphism possible?

Answer

Method overriding.


Can parent references store child objects?

Answer

Yes.


Which operator checks object type?

Answer
instanceof

Summary

Polymorphism allows:

✅ One interface

✅ Multiple implementations

✅ Cleaner code

✅ Extensible systems

✅ Enterprise architecture


Real PocketMine Architecture

Entity

├── Player
├── Zombie
├── ItemEntity
└── Animal

Example:

function process(
Entity $entity
) {

$entity->setNameTag(
"Processed"
);

}

Works for every entity type.

This is polymorphism.


References

https://www.php.net/manual/en/language.oop5.polymorphism.php


Next Chapter

➡ Abstraction

➡ Interfaces

➡ Abstract Classes