Heim > Artikel > Backend-Entwicklung > Ausführliche Erklärung der Eigenschaften in Yii
In diesem Artikel werden hauptsächlich die Eigenschaften (Eigenschaften) im Yii-Framework von PHP vorgestellt und die Schritte zum Implementieren von Eigenschaften ausführlich erläutert. Ich hoffe, es hilft allen.
In PHP werden Klassenmitgliedsvariablen auch Eigenschaften genannt. Sie sind Teil der Klassendefinition und werden verwendet, um den Zustand einer Instanz darzustellen (d. h. um zwischen verschiedenen Instanzen der Klasse zu unterscheiden). In der konkreten Praxis möchten wir häufig eine etwas spezielle Methode zum Lesen und Schreiben von Attributen verwenden. Wenn Sie beispielsweise jedes Mal einen Trimmvorgang für das Etikettenattribut durchführen müssen, können Sie dies mit dem folgenden Code erreichen:
$object->label = trim($label);
Der Nachteil des obigen Codes besteht darin, dass das Etikettenattribut so lange wie möglich ist geändert wird, muss die Funktion trim() erneut aufgerufen werden. Wenn Sie das Etikettenattribut in Zukunft auf andere Weise behandeln müssen, z. B. durch Großschreibung des ersten Buchstabens, müssen Sie den gesamten Code ändern, der dem Etikettenattribut Werte zuweist. Diese Duplizierung des Codes kann zu Fehlern führen und diese Praxis muss natürlich wann immer möglich vermieden werden.
Um dieses Problem zu lösen, führt Yii eine Basisklasse namens yiibaseObject ein, die die Definition von Eigenschaften basierend auf Getter- und Setter-Methoden (Reader und Setter) innerhalb der Klasse unterstützt. Wenn eine Klasse diese Funktion unterstützen muss, muss sie nur yiibaseObject oder seine Unterklassen erben.
Ergänzung: Fast jede Kernklasse des Yii-Frameworks erbt von yiibaseObject oder seinen Unterklassen. Das bedeutet, dass Sie jedes Mal, wenn Sie eine Getter- oder Setter-Methode in einer Kernklasse sehen, diese wie eine Eigenschaft aufrufen können.
Getter-Methoden sind Methoden, deren Namen mit get beginnen, während die Namen von Setter-Methoden mit set beginnen. Der Teil nach get oder set im Methodennamen definiert den Namen der Eigenschaft. Wie im folgenden Code gezeigt, bearbeiten die Getter-Methode getLabel() und die Setter-Methode setLabel() das Label-Attribut:
namespace app\components; use yii\base\Object; class Foo extend Object { private $_label; public function getLabel() { return $this->_label; } public function setLabel($value) { $this->_label = trim($value); } }
(Detaillierte Erklärung: Die Getter- und Setter-Methoden erstellen ein Attribut namens label, In diesem Beispiel zeigt es auf eine private interne Eigenschaft (_label).
Die durch Getter/Setter definierten Eigenschaften werden auf die gleiche Weise wie Klassenmitgliedsvariablen verwendet. Der Hauptunterschied zwischen den beiden besteht darin, dass beim Lesen dieser Eigenschaft die entsprechende Getter-Methode aufgerufen wird, und wenn der Eigenschaft ein Wert zugewiesen wird, wird die entsprechende Setter-Methode aufgerufen. Beispiel:
// 等效于 $label = $object->getLabel(); $label = $object->label; // 等效于 $object->setLabel('abc'); $object->label = 'abc';
Eigenschaften, die nur Getter und keine Setter definieren, sind schreibgeschützte Eigenschaften. Der Versuch, einer solchen Eigenschaft eine Zuweisung zuzuweisen, führt zu einer Ausnahme vom Typ yiibaseInvalidCallException (ungültiger Aufruf). Ebenso sind Eigenschaften, die nur mit Setter-Methoden, aber ohne Getter-Methoden definiert wurden, schreibgeschützte Eigenschaften, und Versuche, solche Eigenschaften zu lesen, lösen ebenfalls eine Ausnahme aus. Es gibt fast keine Fälle für die Verwendung von Nur-Schreib-Attributen.
Eigenschaften, die durch Getter und Setter definiert werden, unterliegen auch einigen besonderen Regeln und Einschränkungen:
Bei den Namen solcher Eigenschaften wird die Groß-/Kleinschreibung nicht beachtet. Beispielsweise sind $object->label und $object->Label dieselbe Eigenschaft. Weil bei PHP-Methodennamen die Groß-/Kleinschreibung nicht beachtet wird.
Wenn der Name dieses Attributtyps mit dem Namen der Klassenmitgliedsvariablen übereinstimmt, hat letztere Vorrang. Angenommen, die obige Foo-Klasse verfügt über eine Label-Mitgliedsvariable und weist dann $object->label = 'abc' einen Wert zu, der dieser Mitgliedsvariablen und nicht der Setter-setLabel()-Methode zugewiesen wird.
Diese Art von Eigenschaft unterstützt keine Sichtbarkeit (Zugriffsbeschränkungen). Ob die Getter- und Setter-Methoden einer Eigenschaft öffentlich, geschützt oder privat sind, hat keinen Einfluss auf die Sichtbarkeit der Eigenschaft.
Die Getter- und Setter-Methoden dieses Eigenschaftstyps können nur als nicht statisch definiert werden. Wenn sie als statische Methoden (statisch) definiert sind, werden sie nicht auf die gleiche Weise verarbeitet.
Um auf das eingangs erwähnte Problem zurückzukommen: Anstatt die Funktion trim() überall aufzurufen, müssen wir sie jetzt nur noch einmal innerhalb der Setter-Methode setLabel() aufrufen. Wenn eine neue Anforderung besteht, dass der erste Buchstabe der Bezeichnung großgeschrieben werden muss, müssen wir nur die Methode setLabel() ändern, ohne anderen Code zu berühren.
Schritte zum Implementieren von Attributen
Wir wissen, dass beim Lesen und Schreiben einer nicht vorhandenen Mitgliedsvariablen eines Objekts automatisch __get() __set() aufgerufen wird. Yii macht sich dies zunutze, um Unterstützung für Attribute bereitzustellen. Aus dem obigen Code können Sie ersehen, dass Yii die Funktion mit dem Namen getpropertyname() aufruft, wenn Sie auf eine bestimmte Eigenschaft eines Objekts zugreifen. Beispielsweise ruft SomeObject->Foo automatisch SomeObject->getFoo() auf. Wenn eine Eigenschaft geändert wird, wird die entsprechende Setter-Funktion aufgerufen. Beispielsweise ruft SomeObject->Foo = $someValue automatisch SomeObject->setFoo($someValue) auf.
Um Eigenschaften zu implementieren, gibt es normalerweise drei Schritte:
Erbt von yiibaseObject .
Deklarieren Sie eine private Mitgliedsvariable, die zum Speichern dieser Eigenschaft verwendet wird.
Stellt Getter- oder Setter-Funktionen oder beides für den Zugriff auf und die Änderung der oben genannten privaten Mitgliedsvariablen bereit. Wenn nur der Getter bereitgestellt wird, ist die Eigenschaft schreibgeschützt, und wenn nur der Setter bereitgestellt wird, ist die Eigenschaft schreibgeschützt.
Die folgende Post-Klasse implementiert das lesbare und beschreibbare Attribut title:
class Post extends yii\base\Object // 第一步:继承自 yii\base\Object { private $_title; // 第二步:声明一个私有成员变量 public function getTitle() // 第三步:提供getter和setter { return $this->_title; } public function setTitle($value) { $this->_title = trim($value); } }
Theoretisch schreiben Sie privaten $_title als öffentlichen $title. Es ist auch möglich zu lesen und schreiben Sie $post->title. Aber das ist keine gute Angewohnheit, und hier ist der Grund:
Die Kapselung der Klasse geht verloren. Im Allgemeinen ist es eine gute Programmierpraxis, Mitgliedsvariablen für die Außenwelt unsichtbar zu machen. Von hier aus sehen Sie es vielleicht nicht, aber wenn Sie eines Tages nicht möchten, dass Benutzer den Titel ändern, wie ändern Sie ihn dann? Wie kann sichergestellt werden, dass der Titel nicht direkt im Code geändert wird? Wenn ein Setter bereitgestellt wird und der Setter gelöscht wird, wird eine Ausnahme ausgelöst, wenn ungereinigte Schreibvorgänge in den Header vorliegen. Wenn Sie die öffentliche $title-Methode verwenden, können Sie Schreibausnahmen überprüfen, indem Sie sie in private $title ändern, aber auch das Lesen ist verboten.
Beim Schreiben von Titeln möchten Sie Leerzeichen entfernen. Bei Verwendung der Setter-Methode müssen Sie an dieser Stelle nur trim() aufrufen, wie im obigen Codeausschnitt. Wenn Sie jedoch die öffentliche Methode $title verwenden, besteht kein Zweifel daran, dass trim() bei jeder Schreibanweisung aufgerufen wird. Können Sie garantieren, dass nichts fehlt?
Daher ist die Verwendung von public $title nur schnell und scheint einfach zu sein, zukünftige Änderungen werden jedoch mühsam sein. Man kann sagen, dass es ein Albtraum ist. Dies ist die Bedeutung des Software-Engineerings, nämlich die einfache Wartung und Änderung des Codes durch bestimmte Methoden. Es mag auf den ersten Blick unnötig erscheinen, aber tatsächlich werden Freunde, die Verluste erlitten haben oder vom Chef des Kunden gezwungen wurden, den vom vorherigen Programmierer geschriebenen Code zu ändern und seine Verwandten zu begrüßen, das Gefühl haben, dass dies sehr notwendig ist.
Allerdings gibt es auf dieser Welt keine Absolutheiten. Da __get() und __set() alle Mitgliedsvariablen durchlaufen, werden sie nur aufgerufen, wenn keine passende Mitgliedsvariable gefunden wird. Daher ist seine Effizienz von Natur aus geringer als die Verwendung von Mitgliedsvariablen. In einigen einfachen Situationen, in denen Datenstrukturen, Datensammlungen usw. dargestellt werden und keine Lese-/Schreibkontrolle erforderlich ist, können Sie die Verwendung von Mitgliedsvariablen als Attribute in Betracht ziehen, was die Effizienz verbessern kann.
Ein weiterer kleiner Trick zur Verbesserung der Effizienz ist: Verwenden Sie $pro = $object->getPro() anstelle von $pro = $object->pro und verwenden Sie stattdessen $objcect->setPro($value). von $object->pro = $value. Dies hat genau den gleichen funktionalen Effekt, vermeidet jedoch die Verwendung von __get() und __set(), was einer Umgehung des Traversal-Prozesses gleichkommt.
Ich denke, hier sollte jemand den Attributmechanismus endlich implementieren, nur um den Entwicklern die Arbeit zu erleichtern. Ich bin jedoch hier, um Ihnen beizubringen, wie Sie die ursprüngliche Methode verwenden, um die sogenannte Effizienz zu verbessern. Tatsächlich besteht ein gewisser Widerspruch zwischen der Bequemlichkeit der Entwicklung und der hohen Effizienz der Ausführung. Mein persönlicher Standpunkt tendiert eher dazu, den Komfort in den Vordergrund zu stellen und die günstigen Bedingungen, die Yii für uns schafft, sinnvoll zu nutzen. Was die Effizienz betrifft, muss das Framework selbst mehr darauf achten. Solange wir keinen zusätzlichen Code schreiben, ist es in Ordnung.
Aber Sie können sicher sein, dass im Yii-Framework Code wie $app->request selten vorkommt, stattdessen wird $app->getRequest() verwendet. Mit anderen Worten: Das Framework selbst legt besonderen Wert auf Effizienz und die Benutzerfreundlichkeit bleibt den Entwicklern überlassen. Kurz gesagt, hier ist nur ein Wissenspunkt. Ob und wie Sie es verwenden, liegt ganz bei Ihnen.
Es ist erwähnenswert:
Da der Zeitpunkt des automatischen Aufrufs von __get() und __set() nur beim Zugriff auf nicht vorhandene Mitgliedsvariablen auftritt. Wenn daher die Mitgliedsvariable public $title definiert ist, werden sie auch dann nicht aufgerufen, wenn getTitle() setTitle() definiert ist. Da $post->title direkt auf den öffentlichen $title verweist, wird __get() __set() nicht aufgerufen. Es wurde von der Wurzel abgetrennt.
Da PHP bei Klassenmethoden nicht zwischen Groß- und Kleinschreibung unterscheidet, rufen $post->getTitle() und $post->gettitle() dieselbe Funktion auf. Daher sind $post->title und $post->Title dieselbe Eigenschaft. Das heißt, auch bei Attributnamen wird die Groß-/Kleinschreibung nicht beachtet.
Da __get() und __set() beide öffentlich sind, ist es bedeutungslos und kann von außen aufgerufen werden, unabhängig davon, ob getTitle() setTitle() als öffentlich, privat oder geschützt deklariert ist. Daher sind alle Eigenschaften öffentlich.
Da __get() und __set() nicht statisch sind, gibt es keine Möglichkeit, statische Attribute zu verwenden.
Andere attributbezogene Methoden von Object
Zusätzlich zu __get() __set() bietet yiibaseObject auch die folgenden Methoden, um die Verwendung von Attributen zu erleichtern:
__isset() wird verwendet, um zu testen, ob der Eigenschaftswert nicht null ist, und wird automatisch aufgerufen, wenn isset($object->property). Beachten Sie, dass diese Eigenschaft über einen entsprechenden Getter verfügen muss.
__unset() wird verwendet, um den Eigenschaftswert auf Null zu setzen und wird automatisch aufgerufen, wenn unset($object->property) ist. Beachten Sie, dass diese Eigenschaft über einen entsprechenden Setter verfügen muss.
hasProperty() wird verwendet, um zu testen, ob eine bestimmte Eigenschaft vorhanden ist. Das heißt, es wird ein Getter oder Setter definiert. Wenn der Parameter $checkVars = true von hasProperty() (der Standardwert ist true), wird davon ausgegangen, dass jede Mitgliedsvariable mit demselben Namen ebenfalls über diese Eigenschaft verfügt, beispielsweise der zuvor erwähnte öffentliche $title.
canGetProperty() testet, ob eine Eigenschaft lesbar ist. Die Bedeutung des Parameters $checkVars ist die gleiche wie oben. Solange der Getter definiert ist, ist die Eigenschaft lesbar. Auch wenn $checkVars true ist. Solange die Klasse Mitgliedsvariablen definiert, unabhängig davon, ob sie öffentlich, privat oder geschützt sind, gelten sie als lesbar.
canSetProperty() testet, ob eine Eigenschaft beschreibbar ist. Die Bedeutung des Parameters $checkVars ist dieselbe wie oben. Solange der Setter definiert ist, kann die Eigenschaft geschrieben werden. Gleichzeitig ist $checkVars true . Solange die Klasse Mitgliedsvariablen definiert, unabhängig davon, ob sie öffentlich, privat oder geschützt sind, gelten sie als beschreibbar.
Objekt und Komponente
yiibaseComponent erbt von yiibaseObject und verfügt daher auch über grundlegende Funktionen wie Eigenschaften.
Da Component jedoch auch Ereignisse und Verhalten einführt, erbt es nicht einfach die Eigenschaftsimplementierungsmethode von Object, sondern überlädt Funktionen wie __get() __set() basierend auf demselben Mechanismus. Was den Implementierungsmechanismus betrifft, sind sie jedoch gleich. Das Verständnis wird dadurch nicht beeinträchtigt.
Wie bereits erwähnt, ist Yii offiziell als komponentenbasiertes Framework positioniert. Das Konzept der sichtbaren Komponenten ist die Grundlage von Yii. Wenn Sie daran interessiert sind, den Quellcode oder die API-Dokumentation von Yii zu lesen, werden Sie feststellen, dass fast alle Kernklassen von Yii von yiibaseComponent abgeleitet (geerbt) sind.
In Yii1.1 gab es bereits eine Komponente, damals CComponent. Yii2 teilt CComponent in Yii1.1 in zwei Klassen auf: yiibaseObject und yiibaseComponent.
Unter diesen ist Object relativ leichtgewichtig und definiert die Eigenschaften der Klasse durch Getter und Setter. Die Komponente ist vom Objekt abgeleitet und unterstützt Ereignisse und Verhalten. Daher weist die Komponentenklasse drei wichtige Merkmale auf:
Eigenschaft
Ereignis
Verhalten
Ich glaube, Sie haben mehr oder weniger verstanden, dass diese drei Funktionen wichtige Einstiegspunkte für die Bereicherung und Erweiterung von Klassenfunktionen und die Änderung des Klassenverhaltens sind. Daher hat Component in Yii einen sehr hohen Stellenwert.
Component bietet zwar mehr Funktionen und Komfort, hat aber die beiden Funktionen Ereignis und Verhalten hinzugefügt, was die Entwicklung erleichtert, aber gleichzeitig gewisse Effizienz opfert. Wenn Sie die beiden Funktionen Ereignis und Verhalten während der Entwicklung nicht verwenden müssen, z. B. eine Klasse, die einige Daten darstellt. Dann können Sie von Object statt von Component erben. Ein typisches Anwendungsszenario ist die Verwendung von Object, wenn es einen vom Benutzer eingegebenen Datensatz darstellt. Und wenn Sie das Verhalten des Objekts und die Ereignisse verarbeiten müssen, die auf die Verarbeitung reagieren können, besteht kein Zweifel daran, dass Component verwendet werden sollte. Im Hinblick auf die Effizienz ist Object näher an der nativen PHP-Klasse, daher sollte Object nach Möglichkeit zuerst verwendet werden.
Verwandte Empfehlungen:
Detaillierte Erläuterung des Yii-Betriebsmechanismus und der Routing
Wie Yii index.php in der URL versteckt
Zusammenfassung der Datenbankabfragevorgänge des PHP-Yii-Frameworks
Das obige ist der detaillierte Inhalt vonAusführliche Erklärung der Eigenschaften in Yii. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!