Heim >Backend-Entwicklung >PHP-Problem >Was ist der Unterschied zwischen Schnittstelle und abstrakter Klasse in PHP?

Was ist der Unterschied zwischen Schnittstelle und abstrakter Klasse in PHP?

青灯夜游
青灯夜游Original
2021-03-15 17:29:575237Durchsuche

Der Unterschied ist: 1. Die Schnittstelle wird durch das Schlüsselwort interface definiert, und die abstrakte Klasse wird durch das Schlüsselwort abstract definiert. 2. Die Schnittstelle hat keine Datenmitglieder, aber die abstrakte Klasse hat Datenmitglieder, und die abstrakte Klasse kann kapseln Sie Daten; 3. Schnittstellen haben keine Konstruktoren, während abstrakte Klassen Konstruktoren haben können.

Was ist der Unterschied zwischen Schnittstelle und abstrakter Klasse in PHP?

Die Betriebsumgebung dieses Tutorials: Windows 7-System, PHP-Version 7.1, DELL G3-Computer

1. Der Unterschied zwischen abstrakten Klassen und Schnittstellen

Wenn Sie PHP objektorientiert lernen, werden Sie sich immer darauf konzentrieren über abstrakte Klassen und Schnittstellen Verwirrt, warum kann man so leicht verwechseln, wenn die Funktionen fast gleich sind? Warum nicht eine weglassen? Tatsächlich ist der Unterschied zwischen den beiden jedoch immer noch sehr groß. Wenn Sie die beiden Methoden von PHP gut nutzen können, wird die objektorientierte Programmierung sinnvoller, klarer und effizienter.

a. Die Schnittstelle wird durch das Schlüsselwort interface definiert, und die abstrakte Klasse wird durch das Schlüsselwort abstract definiert.
b. Die Verwendung von Schnittstellen wird über das Schlüsselwort „implementiert“ implementiert, während die Operation abstrakter Klassen über das Schlüsselwort „extends“ der Klassenvererbung implementiert wird. Achten Sie bei der Verwendung besonders darauf.
c. Schnittstellen haben keine Datenmitglieder, aber abstrakte Klassen haben Datenmitglieder und abstrakte Klassen können Daten kapseln.
d. Schnittstellen haben keine Konstruktoren, während abstrakte Klassen Konstruktoren haben können.
e. Die Methoden in der Schnittstelle sind alle öffentliche Typen, während die Methoden in der abstrakten Klasse durch private, geschützte oder öffentliche Typen geändert werden können.
f. Eine Klasse kann mehrere Schnittstellen gleichzeitig implementieren, aber nur eine abstrakte Klasse.

Gleiche Punkte: In den Funktionskörpern abstrakter Methoden und Schnittstellen kann nichts geschrieben werden, nicht einmal zwei geschweifte Klammern! ! ! Zum Beispiel: function getName(); Das ist es

2. Schnittstelle

Mit einer Schnittstelle (Schnittstelle) können Sie angeben, welche Methoden eine bestimmte Klasse implementieren muss, Sie müssen jedoch nicht den spezifischen Inhalt dieser Methoden definieren .

Eine Schnittstelle wird über das Schlüsselwort interface definiert, genau wie die Definition einer Standardklasse, aber alle darin definierten Methoden sind leer.

Alle in der Schnittstelle definierten Methoden müssen öffentlich sein. Dies ist eine Eigenschaft der Schnittstelle.

Implementierungen

Um eine Schnittstelle zu implementieren, verwenden Sie den Implements-Operator. Die Klasse muss alle in der Schnittstelle definierten Methoden implementieren, andernfalls wird ein schwerwiegender Fehler gemeldet. Eine Klasse kann mehrere Schnittstellen implementieren. Verwenden Sie Kommas, um die Namen mehrerer Schnittstellen zu trennen.

Hinweis:
Bei der Implementierung mehrerer Schnittstellen dürfen die Methoden in den Schnittstellen nicht denselben Namen haben.

Hinweis:
Schnittstellen können auch vererbt werden, indem der Extens-Operator verwendet wird.

Hinweis:
Um eine Schnittstelle zu implementieren, muss eine Klasse genau dieselbe Methode verwenden wie die in der Schnittstelle definierte Methode. Andernfalls kommt es zu einem schwerwiegenden Fehler.

Konstanten

Konstanten können auch in Schnittstellen definiert werden. Schnittstellenkonstanten werden genauso verwendet wie Klassenkonstanten, können jedoch nicht von Unterklassen oder Unterschnittstellen überschrieben werden.

 <?php

// 声明一个&#39;iTemplate&#39;接口
interface iTemplate
{
    public function setVariable($name, $var);
    public function getHtml($template);
}


// 实现接口
// 下面的写法是正确的
class Template implements iTemplate
{
    private $vars = array();

    public function setVariable($name, $var)
    {
        $this->vars[$name] = $var;
    }

    public function getHtml($template)
    {
        foreach($this->vars as $name => $value) {
            $template = str_replace('{' . $name . '}', $value, $template);
        }

        return $template;
    }
}

// 下面的写法是错误的,会报错,因为没有实现 getHtml():
// Fatal error: Class BadTemplate contains 1 abstract methods
// and must therefore be declared abstract (iTemplate::getHtml)
class BadTemplate implements iTemplate
{
    private $vars = array();

    public function setVariable($name, $var)
    {
        $this->vars[$name] = $var;
    }
}
?>
Example #2 可扩充的接口

<?php
interface a
{
    public function foo();
}

interface b extends a
{
    public function baz(Baz $baz);
}

// 正确写法
class c implements b
{
    public function foo()
    {
    }

    public function baz(Baz $baz)
    {
    }
}

// 错误写法会导致一个致命错误
class d implements b
{
    public function foo()
    {
    }

    public function baz(Foo $foo)
    {
    }
}
?>
Example #3 继承多个接口

<?php
interface a
{
    public function foo();
}

interface b
{
    public function bar();
}

interface c extends a, b
{
    public function baz();
}

class d implements c
{
    public function foo()
    {
    }

    public function bar()
    {
    }

    public function baz()
    {
    }
}
?>
Example #4 使用接口常量

<?php
interface a
{
    const b = &#39;Interface constant&#39;;
}

// 输出接口常量
echo a::b;

// 错误写法,因为常量不能被覆盖。接口常量的概念和类常量是一样的。
class b implements a
{
    const b = &#39;Class constant&#39;;
}
?>

http://php.net/manual/zh/sprache.oop5.interfaces.php

3. Abstrakte Klassen

PHP 5 unterstützt abstrakte Klassen und abstrakte Methoden. Als abstrakt definierte Klassen können nicht instanziiert werden. Jede Klasse muss als abstrakt deklariert werden, wenn mindestens eine Methode darin als abstrakt deklariert ist. Eine als abstrakt definierte Methode deklariert nur ihre aufrufende Methode (Parameter) und kann nicht ihre spezifische Funktionsimplementierung definieren.

Beim Erben einer abstrakten Klasse muss die Unterklasse alle abstrakten Methoden in der übergeordneten Klasse definieren. Außerdem muss die Zugriffskontrolle dieser Methoden dieselbe (oder entspannter) sein wie in der übergeordneten Klasse. Wenn beispielsweise eine abstrakte Methode als geschützt deklariert ist, sollte die in der Unterklasse implementierte Methode als geschützt oder öffentlich deklariert werden und kann nicht als privat definiert werden. Darüber hinaus müssen die aufrufenden Methoden übereinstimmen, d. h. Art und Anzahl der erforderlichen Parameter müssen konsistent sein. Wenn beispielsweise eine Unterklasse einen optionalen Parameter definiert, der nicht in der Deklaration einer abstrakten Methode der übergeordneten Klasse enthalten ist, besteht kein Konflikt zwischen den beiden Deklarationen. Dies gilt auch für Konstruktoren seit PHP 5.4. Konstruktordeklarationen vor PHP 5.4 könnten unterschiedlich sein.

<?php
abstract class AbstractClass
{
 // 强制要求子类定义这些方法
    abstract protected function getValue();
    abstract protected function prefixValue($prefix);

    // 普通方法(非抽象方法)
    public function printOut() {
        print $this->getValue() . "\n";
    }
}

class ConcreteClass1 extends AbstractClass
{
    protected function getValue() {
        return "ConcreteClass1";
    }

    public function prefixValue($prefix) {
        return "{$prefix}ConcreteClass1";
    }
}

class ConcreteClass2 extends AbstractClass
{
    public function getValue() {
        return "ConcreteClass2";
    }

    public function prefixValue($prefix) {
        return "{$prefix}ConcreteClass2";
    }
}

$class1 = new ConcreteClass1;
$class1->printOut();
echo $class1->prefixValue('FOO_') ."\n";

$class2 = new ConcreteClass2;
$class2->printOut();
echo $class2->prefixValue('FOO_') ."\n";
?>
以上例程会输出:

ConcreteClass1
FOO_ConcreteClass1
ConcreteClass2
FOO_ConcreteClass2
Example #2 抽象类示例

<?php
abstract class AbstractClass
{
    // 我们的抽象方法仅需要定义需要的参数
    abstract protected function prefixName($name);

}

class ConcreteClass extends AbstractClass
{

    // 我们的子类可以定义父类签名中不存在的可选参数
    public function prefixName($name, $separator = ".") {
        if ($name == "Pacman") {
            $prefix = "Mr";
        } elseif ($name == "Pacwoman") {
            $prefix = "Mrs";
        } else {
            $prefix = "";
        }
        return "{$prefix}{$separator} {$name}";
    }
}

$class = new ConcreteClass;
echo $class->prefixName("Pacman"), "\n";
echo $class->prefixName("Pacwoman"), "\n";
?>
以上例程会输出:

Mr. Pacman
Mrs. Pacwoman
老代码中如果没有自定义类或函数被命名为“abstract”,则应该能不加修改地正常运行。

http://php.net/manual/zh/sprache.oop5.abstract.php

Empfohlenes Lernen: „PHP-Video-Tutorial

Das obige ist der detaillierte Inhalt vonWas ist der Unterschied zwischen Schnittstelle und abstrakter Klasse in PHP?. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Stellungnahme:
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn