Abstract Class vs Interface
Tags: php
Published: 2020-01-28 09:44:09

---
title: Abstract Class vs Interface
published: true
tags: php
canonical_url: 
---

I found this picture that tells the difference between `abstract class` and `interface`:

![enter image description here](https://codeinphp.github.io/images/142937584655328b66dcedc.png)

* * *

Let's see each comparison practically so we know what it means.

```
Interface support multiple inheritance | Abstract class does not support multiple inheritance
```

It means you can extend an `interface` with one or more (hence _multiple inheritance_) interfaces like:

```
interface Interface_A { }
interface Interface_B { }
interface Interface_C { }

interface MyInterface extends Interface_A, Interface_B, Interface_C { }
```

As can be seen, we are extending `MyInterface` with three other interfaces `Interface_A`, `Interface_A` and `Interface_C`.

Let's now try to extend an `abstract class`:

```
class Class_A { }

abstract class MyAbstractClass extends Class_A { }
```

No problem there, you CAN extend an abstract class with exactly one class but if you try to add one more:

```
class Class_A { }
class Class_B { }

abstract class MyAbstractClass extends Class_A, Class_B { }
```

This time PHP would give you strange error without telling you what you are doing wrong:

`Parse error: syntax error, unexpected ',', expecting '{'`

I wish PHP would have given message somewhat like (hope PHP gives smarter error messages in future versions):

`Fatal Error: You cannot extend an abstract class with more than one classes`

* * *

```
Interface does'n Contains Data Member | Abstract class contains Data Member
```

By data members, it means class properties or variables. So you cannot add data members to an interface:

```
interface MyInterface {
    public $foo = null;
}
```

So in an interface, only method stubs can be provided.

You can add data members to an abstract class though, this is valid code of course:

```
abstract class MyAbstractClass {
    public $foo = null;
}
```

* * *

```
Interface does'n contains Constructors | Abstract class contains Constructors
```

It sounds like this point applies to may be other languages but in PHP an interface CAN have an empty constructor shell:

```
interface MyInterface {
    public function __construct();
}
```

Like other languages, PHP shouldn't have allowed having a constructor inside an interface. But anyways, it doesn't make much sense here and should be avoided anyway.

On the other hand, an abstract class can contain constructor method:

```
abstract class MyAbstractClass {
    abstract public function __construct();
}
```

Here constructor is said to be `abstract` and therefore expends child classes to complement for it. However, you can also have common initialization code in constructor of an abstract class too in which case, you would need to remove the `abstract` keyword and provide the body for it:

```
abstract class MyAbstractClass {
    public function __construct() {
         // initialization code
    };
}
```

* * *

```
An interface Contains only incomplete member (signature of member) | An abstract class Contains both incomplete (abstract) and complete member
```

This simply means an interface can only contain method stubs not their implementation. This is pretty same as second point in the image above. This is why in methods of an interface, they don't have bodies marked with `{ }` braces. So an interface is completely empty shell that enforces some rules that child classes must implement and that's it.

Abstract classes can have both; empty method definitions as well as full method implementation. Generally empty method stubs are prefixed with `abstract` keyword so that child classes must provide their implementation details. But an abstract class can also contain full method implementation inside it which are generally used for common piece of functionality that each child class may need. For example:

```
abstract class Animal {
    // child classes must implement this
    abstract function prey();

    public function run() {
        echo 'I am running!';
    }
}

class Dog extends Animal {
    public function prey() {
        echo 'I killed the cat !';
    }
}

class Cat extends Animal {
    public function prey() {
        echo 'I killed the rat !';
    }
}

$dog = new Dog();
$cat = new Cat();

$dog->prey(); // I killed the cat !
$cat->prey(); // I killed the rat !

$dog->run(); // I am running!
$cat->run(); // I am running!
```

In above code, we can see that `Animal` class has one `abstract` method called `prey` because each child class (animal) have their own ways of finding prey and a full implemented method called `run` because all animals can run, this doesn't need to be defined in each of child classes. So here `run` method is fully implemented and represents common data that needs to be shared across child classes.

Notice that other than common fully implemented methods inside an abstract class, you can also have common data members eg variables that need to be shared across child classes.

* * *

```
An interface cannot have access modifiers by default everything is assumed as public | An abstract class can contain access modifiers for the subs, functions, properties
```

By access modifiers, we mean ability to change scoping by using keywords like [`public`, `private` and `protected`](http://stackoverflow.com/questions/4361553/php-public-private-protected). We cannot use these for interfaces but we can use them for everything in abstract classes.

* * *

```
Members of interface can not be Static | Only Complete Member of abstract class can be Static
```

This is again possible in PHP (as of now with PHP 5.4) unlike other languages, so you CAN do:

```
interface MyInterface {
    static function foo();
}
```

Notice the addition of keyword `static` to mark it as static method.

For abstract class, you can have static members as well as those methods that are implemented in the abstract class:

```
abstract class MyAbstractClass {
    public static $foo = null;

    public static function foo() {}
}
```

But you cannot have a method to be both `static` and `abstract`, so you cannot do this, which is common across the languages:

```
abstract class MyAbstractClass {
    public static $foo = null;

    abstract static function foo() {} // error
}
```

* * *

In conclusion, interface and abstract classes are completely different from each other, you cannot interchange them or use one as alternative over the other. Interfaces are completely empty shells that expect child classes to implement everything for them. On the other hand, abstract class can not only contain _common piece of information_ by implementing inside them but also expect child classes to fill in the remaining gaps.

 ![](http://feeds.feedburner.com/~r/codeinphpfeed/~4/BXVBGV9K0CE)