Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Type hinting in interface

Tags:

oop

php

interface

Why should the class type-hint be 100% same with the interface?
I mean, why can't it accept implementing class as type hint?

To make it clear,

<?php
interface MyInterface
{
    public function doMethod(SomeInterface $a)
    {
    }
}

class MyClass implements MyInterface
{
    public function doMethod(ClassThatImplementsSomeInterface $a)
     {
     }
}

Error: Fatal error: Declaration of MyClass::doMethod() must be compatible with that of MyInterface::doMethod()

Since the class type hinting implements SomeInterface, I expect it doesn't break the contract.
Why do I want it? Because of the advantages of interface flexibility.
The same goes for abstract class.
If I rewrite the code so that method 'do' has no type-hint, I know that it will 'fix' it.
But, somehow I think I should define the contract that type-hinting of $a must implement SomeInterface.
And, Why don't I just use the same type-hint which is SomeInterface ?
That's because there are methods that don't exist in SomeInterface that I need.
So, what's the point of this limitation?

Reproducable codepad: http://codepad.org/2PLd8AmV

like image 437
Terry Djony Avatar asked Jun 07 '16 13:06

Terry Djony


1 Answers

The answer is simply, that you need to be able to rely on the object that the interface requires.

Real world example:

Interface requires APPLE.

You now try to implement a class that says I require a GREEN APPLE (it's still an apple!).

Someone now tries to implement your INTERFACE and put it into the class for the green apple. He tries to put in a RED APPLE which is compatible with APPLE but not with GREEN APPLE.

=> bang, contract broken!

Coding example:

interface MyInterface
{
    public function doMethod(SomeInterface $a);
}

class MyClass implements MyInterface
{
    public function doMethod(ClassThatImplementsSomeInterface $a) { }
}

class DifferentClass implements SomeInterface { }

$ding = new MyClass();
$ding->doMethod(new DifferentClass);

This wouldn't work because DifferentClass is not ClassThatImplementsSomeInterface!

like image 181
Daniel W. Avatar answered Sep 25 '22 02:09

Daniel W.