Heim  >  Artikel  >  Backend-Entwicklung  >  Zusammenfassung der fünf Prinzipien des objektorientierten PHP-Designs (SOLID)

Zusammenfassung der fünf Prinzipien des objektorientierten PHP-Designs (SOLID)

不言
不言Original
2018-07-13 15:58:592113Durchsuche

Dieser Artikel stellt hauptsächlich die Zusammenfassung der fünf Prinzipien des objektorientierten PHP-Designs (SOLID) vor, die einen gewissen Referenzwert haben. Jetzt können Freunde in Not darauf verweisen

PHP Designprinzipien Um es zu klären, lesen Sie „PHP-Kerntechnologie und Best Practices“, „Agile Entwicklungsprinzipien, Muster und Praktiken“, den Artikel „Fünf Prinzipien des objektorientierten PHP-Designs“, DesignmusterprinzipienSOLID

Einzelne Verantwortung Prinzip, SRP)

Definition/Merkmale
  • Nur ​​ein Grund für eine Klassenänderung

  • Eine Klasse hat nur einen Verantwortung (Verantwortung: Grund für Änderung)

  • Vermeiden Sie die Verteilung der gleichen Verantwortlichkeiten auf verschiedene Klassen und die Duplizierung von Funktionen

Probleme
  • Eine Klasse hat zu viele Verantwortlichkeiten, und die Änderung einer Verantwortlichkeit beeinträchtigt die Fähigkeit dieser Klasse, andere Verantwortlichkeiten zu erfüllen unerwartete Konsequenzen. Zerstören Sie

Vorteile der Einhaltung der SPR-Prinzipien
  • Reduzieren Sie die Kopplung zwischen Klassen : Nur wenn sich die Anforderungen ändern eine ist eine modifizierte Klasse, wodurch die Auswirkungen von Änderungen auf andere Verantwortlichkeiten isoliert werden

  • Verbesserung der Wiederverwendbarkeit von Klassen : Referenz auf Anfrage, eine Klasse ist für eine Verantwortung verantwortlich, Anforderungen Änderungen erfordern lediglich das Ändern der entsprechenden Klasse oder das Hinzufügen einer bestimmten Verantwortung

  • Reduzieren Sie die Komplexität der Klasse: Einzelne Verantwortung, dezentrale Funktionen Reduzieren Sie eine Klasse auf mehrere Verantwortungsklassen Komplexität

Codebeispiel
class ParseText
{
    private $content;
    
    public function decodeText(String $content)
    {
        // TODO: decode content
    }
    
    public function saveText()
    {
        // TODO:: save $this->content;
    }
}
/*
问题思考:
解析的文本类型会有多种-html、xml、json
保存的文本也会有多种途径-redis、mysql、file
客户端只需要解析文本时必须会引入saveText不需要的方法
两个职责之间没有强烈的依赖关系存在
任意职责需求变化都需要更改这个类
*/

/*
符合SRP的设计
职责拆分
*/

class Decoder
{
    private $content;
    
    public function decodeText(String $content)
    {
    // TODO: decode content
    }
    
    public function getText()
    {
        return $this->content;
    }
}

class Store
{
    public function save($content)
    {
        // TODE: save
    }
}
Zusammenfassung

Viele Aufgaben des Softwaredesigns bestehen darin, Verantwortlichkeiten zu entdecken und die Beziehungen zwischen Verantwortlichkeiten sinnvoll zu trennen. Wenn sich Änderungen an der Anwendung immer auf mehrere Verantwortlichkeiten gleichzeitig auswirken, ist keine Trennung der Verantwortlichkeiten erforderlich.

Schnittstellentrennungsprinzip ISP

Problem

Beim Entwerfen einer Anwendung ist die Schnittstelle der Klasse nicht zusammenhängend. Verschiedene Clients enthalten nur einige zentralisierte Funktionen, aber das System zwingt den Client, alle Methoden im Modul zu implementieren und auch einige dumme Methoden zu schreiben. Eine solche Schnittstelle wird zu einer fetten Schnittstelle oder einer Schnittstellenverschmutzung. Eine solche Schnittstelle führt zu unangemessenem Verhalten im System, verschwendet Ressourcen, beeinträchtigt andere Client-Programme, verbessert die Kopplung usw.

ISP-Definition/-Eigenschaften

  • Clients sollten nicht gezwungen werden, sich auf Methoden/Funktionen zu verlassen, die sie nicht benötigen

  • Die Abhängigkeit einer Klasse von einer Klasse sollte auf der kleinsten Schnittstelle basieren

  • Die Implementierungsklasse der Schnittstelle sollte nur als Einzelverantwortungsprinzip dargestellt werden

Vorteile der Befolgung des ISP-Prinzips
  • Bei der Trennung von Fettschnittstellen stellt jede Gruppe von Schnittstellen spezifische Funktionen bereit, um eine bestimmte Gruppe von Clientprogrammen zu bedienen.

  • Änderungen an einer Gruppe von Schnittstellen haben keine oder nur geringfügige Auswirkungen andere Schnittstellen/Client-Programm, um die Reinheit der Schnittstelle sicherzustellen

Lösung

  • Fat-Schnittstelle wird in mehrere kundenspezifische Schnittstellen/mehrere Schnittstellen zerlegt Getrennte Vererbung

  • Mithilfe der Delegation-Trennungsschnittstelle sind zwei Objekte an der Verarbeitung derselben Anfrage beteiligt, und das Objekt, das die Anfrage akzeptiert, delegiert die Anfrage an ein anderes Objekt zur Verarbeitung

Codebeispiel
/*
* 公告接口
*/
interface Employee
{
    public function startWork();
    public function endWork();
}

/*
* 定义特定客户端接口
*/
interface Coder
{
    public function writeCode();
}

interface Ui
{
    public function designPage();
}

class CoderClient implements Employee, Coder
{
    public function startWork()
    {
        //TODO:: start work time
    }
    public function endWork()
    {
        //TODO:: end work time
    }
    
    public function writeCode()
    {
        //TODO:: start write code
        return 'hellow world';
    }
}
$c = new CoderClient();
echo $c->writeCode();
Zusammenfassung

Fat-Klassen können abnormale und schädliche Kopplungsbeziehungen zwischen ihren Clientprogrammen verursachen. Durch die Zerlegung von Thick-Clients in mehrere clientspezifische Schnittstellen sind Clients stark von den Methoden abhängig, die sie tatsächlich aufrufen, wodurch die Abhängigkeiten zwischen Clients und Methoden, die sie nicht aufrufen, gelöst werden. Die Schnittstellenisolation sollte klein und selten gehalten werden.

Vergleich zwischen SRP und ISP
  • Beide lösen das Abhängigkeitsprinzip im Softwaredesign

  • SRP konzentriert sich auf die Aufteilung der Verantwortlichkeiten Bei Constraint-Klassen handelt es sich hauptsächlich um Schnittstellen und Methoden, bei denen es sich um Details und Implementierungen im Programm handelt. ISP achtet auf die Isolation von Schnittstellen. Das abstrakte Design der Schnittstelle erfolgt aus einer eher makroökonomischen Perspektive

Open-Close-Prinzip OCP (Open-Close) Schließen (Prinzip OCP)

Problem

Da die Größe von Softwaresystemen weiter zunimmt, nimmt die Komplexität der Systemwartung und -modifikation weiter zu. Änderungen in einem Teil des Systems wirken sich häufig auf andere Module aus. Die richtige Anwendung der OCP-Prinzipien kann solche Probleme lösen.

Definition/Merkmale
  • Ein Modul sollte im Hinblick auf die Erweiterung des Verhaltens offen und im Hinblick auf die Veränderbarkeit geschlossen sein

Folgen OCP-Vorteile
  • Das Verhalten des Moduls ist erweiterbar und das Verhalten/die Funktion des vorhandenen Moduls kann problemlos erweitert werden

  • Erweiterungen des Moduls Verhalten wird keine/geringe Auswirkungen auf bestehende Systeme/Module haben

Codebeispiele
/*
* 定义有固定行为的抽象接口
*/
interface Process
{
    public function action(String $content);
}

/*
* 继承抽象接口,扩展不同的行为
*/
class WriteToCache implements Process
{
    public function action(String $content)
    {
        return 'write content to cache: '.$content;
    }
}

class ParseText
{
    private $content;
    public function decodeText($content)
    {
        $this->content = $content;
    }
    
    public function addAction(Process $process)
    {
        if ($process instanceof Process) {
            return $process->action($this->content);    
        }
    }
}

$p = new ParseText();
$p->decodeText('content');
echo $p->addAction(new WriteToCache());
Zusammenfassung

Die Kernidee von OCP ist die Abstraktionsschnittstelle Beim Programmieren ist die Abstraktion relativ stabil. Lassen Sie Klassen von festen Abstraktionen abhängen, lassen Sie Klassen Abstraktionen durch objektorientierte Vererbung und Polymorphismus erben und ihre Methoden oder inhärenten Verhaltensweisen überschreiben. Dies dient dazu, über neue Erweiterungsmethoden/-funktionen nachzudenken und Erweiterungen zu erreichen.

里氏替换原则(Liskov Substitution Principle LSP)

问题

面向对象中大量的继承关系十分普遍和简单,这种继承规则是什么,最佳的继承层次的规则又是什么,怎样优雅的设计继承关系,子类能正确的对基类中的某些方法进行重新,这是LSP原则所要处理的问题。

定义/特性
  • 子类必须能够替换掉他们的基类型:任何出现基类的地方都可以替换成子类并且客户端程序不会改变基类行为或者出现异常和错误,反之不行。

  • 客户端程序只应该使用子类的抽象父类,这样可以实现动态绑定(php多态)

违反LSP原则

假设一个函数a,他的参数引用一个基类b,c是b的派生类,如果将c的对象作为b类型传递给a,会导致a出现错误的行为,那没c就违法了LSP原则。

/*
* 基类
*/
class Computer
{
    public function action($a, $b)
    {
        return $a+$b;
    }
}
/*
* 子类复习了父类方法,改变了action 的行为
* 违反了LSP原则
*/
class Client extends Computer
{
    public function action($a, $b)
    {
        return $a-$b;
    }  
}

function run(Computer $computer, $a, $b) {
    return $computer->action($a, $b);
}

echo run((new Client()), 3, 5);
总结

LSP是OCP得以应用的最主要的原则之一,正是因为子类性的可替换行是的基类类型在无需修改的情况下扩展功能。

依赖倒置原则(Depend Inversion Principle DIP)

问题

软件开发设计中,总是倾向于创建一些高层模块依赖底层模块,底层模块更改时直接影响到高层模块,从而迫使他们改变。DIP原则描述了高层次模块怎样调用低层次模块。

定义/特性
  • 高层模块不应该依赖与底层模块,二者都应该依赖于抽象

  • 抽象不应该依赖与细节,细节应该依赖于抽象

代码示例
interface Arithmetic
{
    //public function sub($a, $b);
}

class Client
{
    
    public function computer(Arithmetic $arithmetic, $a, $b)
    {
        return $arithmetic->add($a, $b);
    }
}

class Addition implements Arithmetic
{
    public function add($a, $b)
    {
        return $a + $b;
    }
}

$c = new Client();
echo $c->computer(new Addition(), 2, 3);

/*
client 高层类 依赖于Arithmetic,Addition底层实现细节类实现Arithmetic接口,达到二者依赖于抽象接口的DIP设计原则
*/
总结

DIP原则就是每个高层次模块定义一个它所需服务的接口声明,低层次模块实现这个接口。每个高层次类通过该抽象接口使用服务。

思考

面向对象软件开发中合理的遵循设计原则可以更好的设计代码,减少不必要的错误,提高程序的可维护性,可扩展性和稳定性。

  • 单一职责(SRP)如何正确的划分职责,类的职责单一提高代码复用性,降低耦合性

  • 接口隔离(OCP)合理划分接口功能,保证接口的专一性,纯洁性,减少依赖关系

  • 里氏替换(LSP)合理利用类的继承体系,保证真确的继承关系不被破坏

  • 依赖倒置(DIP)抽象接口编程由于抽象具体实现

  • 开放封闭(OCP)面向对象编程终极目标所达到的结果,类/模块/系统的功能行为可扩展,内部更改性是封闭的

以上就是本文的全部内容,希望对大家的学习有所帮助,更多相关内容请关注PHP中文网!

相关推荐:

对LNMP的运维追踪

Das obige ist der detaillierte Inhalt vonZusammenfassung der fünf Prinzipien des objektorientierten PHP-Designs (SOLID). 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