✅ WEB- och WordPress -nyheter, teman, plugins. Här delar vi tips och bästa webbplatslösningar.

Tittar på polymorfism på djupet

15

När jag startade den här serien pratade jag om de fyra pelarna i objektorienterad programmering. Var och en av dessa ämnen är listade och länkade nedan.

  1. Abstraktion
  2. Inkapsling
  3. Arv
  4. Polymorfism

Vid det här laget skulle jag normalt vilja börja gå vidare till nästa ämne. Innan jag gör det skulle jag dock vilja spendera ett inlägg till med att utforska begreppet polymorfism.

I min karriär har jag hittills sett få ämnen som ger dem som kommer in i objektorienterad programmering mer förvirring och problem än polymorfism. Så jag skulle vilja diskutera det lite mer ingående inom ramen för objektorienterad programmering och utanför någon speciell ram eller applikation (som WordPress).

I det här inlägget kommer jag att göra en snabb genomgång av vad vi har diskuterat hittills, och sedan hoppa tillbaka till polymorfism.

Fördjupad polymorfism

Först, som nämnts, vill jag snabbt granska vad som har diskuterats hittills, särskilt om du har slarvat bort något av de tidigare inläggen.

Oroa dig inte: Inget nedan går ut i kod. Istället definierar den helt enkelt termerna vi har använt så att du har en uppfattning om vad jag syftar på när du ser ordet dyka upp i den här serien.

Abstraktion

Vi abstraherar idén om något till en klass. Istället kommer vi att abstrahera idéer i deras klasser. Och det finns en nyckelidé här: En klass ska representera ett substantiv.

Inkapsling

Inkapsling är egentligen bara ett "stort" ord som hänvisar till idén att hantera sitt ansvar (eller hålla reda på dess data).

Arv

Arv hänvisar till idén att en klass, även om den har sin egen implementering, bokstavligen ärver egenskaper, funktioner och generell implementering från en överordnad klass.

Polymorfism

Polymorfism tillåter oss att referera till en klass av en typ när den kan deklareras som en annan typ.

Med det sagt, det är här jag tror att saker och ting kan bli lite mer komplicerade. I de tidigare inläggen har jag gett ett antal olika kodexempel (och jag uppmanar dig att titta tillbaka på dem).

Men i dagens inlägg ska jag försöka utforska idén lite mer både i förklaring än i kod.

Angående arv

Om det inte är uppenbart vid denna tidpunkt, är polymorfism starkt relaterad till arv. Tänk på det så här: Om en klass ärver egenskaper och metoder från en annan klass, kan den "stå på plats" för den överordnade klassen.

Det betyder att om du har något som en innehållsklass och sedan har två underklasser, en är ett inlägg och en är en sida, kan du instansiera klassen genom att använda referenstypen för innehåll.t

Men vid körning kommer det faktiskt att vara en instans av typen Post . Vettigt? Här är lite kod som exempel.

Först börjar vi med att definiera en innehållsklass :

<?php
class Content {

   protected $title;

   protected $content;

   protected $metadata;

   public function __construct()
   {
     $this->title = "Hello World!";
     $this->content = "This is a sample piece of content.";
     $this->metadata = "<This is the metadata of the post.>";
   }

   public function getTitle()
   {
     return $this->title;
   }

   public function getContent()
   {
     return $this->content;
   }

   public function getMetadata()
   {
     return $this->metadata;
   }
 }

Den har de allmänna egenskaperna som du förmodligen har förväntat dig – titel, innehåll och metadata. Visst, dessa egenskaper är bara strängar men de kan vara mer utarbetade datastrukturer i en verklig situation.

Låt oss nu titta på ett inlägg :

<?php

class Post extends Content  {

   private $author;

   public function __construct() {
     parent::__construct();
     $this->author = "Tom McFarlin";
   }

   public function getAuthor()
   {
     return $this->author;
   }
 }

Vad händer då om du anropar en metod i  klassen Post, som getTitle, som inte existerar men den finns i klassen Content? Sedan på grund av arv kommer den att leta efter metoden i Post, inte hitta den, och sedan börja leta efter den i Innehåll.

Om den hittas kommer den att köra den.

Tittar på polymorfism på djupet

På samma sätt kan vi göra något så här med sidklassen och innehållsdata. Först instansierar vi basklassen och sedan ställer vi in ​​egenskaper som är specifika för sidan. I det här fallet kommer det att bli en kategori.

<?php

class Page extends Content  {

   private $category;

   public function __construct() {
     parent::__construct();
     $this->category = "Articles";
   }

   public function getCategory()
   {
     return $this->category;
   }
 }

Nu när vi kör koden kan vi börja med innehållet:

<?php

$content = new Content();
echo $content->getTitle();

Lägg märke till att detta ser ut som vi förväntar oss eftersom vi har en titel och vi har innehåll. Låt oss också titta på inlägget :

<?php

// These will work because they reside in the Content base class.
$post = new Post();
echo $post->getAuthor();
echo $post->getTitle();

Detta fungerar eftersom vi har en författare men vi har också en titel eftersom den finns i Innehåll. Men om vi försöker ringa getAuthor på en instans av Post?

<?php

// These will work because they reside in the Content base class.
$post = new Post();
echo $post->getAuthor();
echo $post->getTitle();

Vi kommer att få ett fel eftersom metoden inte finns i den klassen.

Tittar på polymorfism på djupet

Så vad ska vi göra? Eftersom vi inte har starka typer i PHP kan vi inte casta det till en annan typ.

Det finns designmönster för detta, som jag kommer att diskutera i en framtida uppsättning inlägg, men PHP tillåter inte detta lika lätt som vissa andra språk (som C# eller Java).

Frågor om polymorfism

Förhoppningsvis ger koden ovan dig en uppfattning om hur en konkret typ som ett inlägg  eller en sida implicit kan ha egenskaperna och metoderna för sin basklass, Content, som används vid körning.

Men det väcker också några frågor, eller hur? Till exempel:

  • Varför är polymorfism användbart? Ytterst handlar det om flexibilitet. Det vill säga, du kan skriva en generisk innehållstyp men sedan skapa ett inlägg eller en sida som vi har sett ovan. Detta ger oss sedan alla fördelar med Content -klassen samtidigt som det ger oss t.ex. Post -klassens specificitet.
  • Detta verkar vara mer förvirrande än flexibelt. På ett sätt är det förvirrande eftersom koden kräver lite spårning. Det vill säga, du kanske börjar i Post -klassen och måste se upp till vad innehållsklassen erbjuder. Å andra sidan gör det det också väldigt enkelt att introducera en ny  underklass för innehåll och sedan använda den när den passar bäst under körning.

När det gäller superklasser och underklasser är det här att ha en solid IDE kommer in i bilden.

Det är alltid trevligt att ha en editor som du gillar, visst, men att ha en som intuitivt kan avgöra vad som är föräldraklassen, vad som är basklassen, etc., kan hjälpa dig att spåra, felsöka, följa och skriva nytt. koda.

Men det är innehåll för ett annat inlägg som kommer efter att vi pratat om designmönster.

Inspelningskälla: tommcfarlin.com

Denna webbplats använder cookies för att förbättra din upplevelse. Vi antar att du är ok med detta, men du kan välja bort det om du vill. Jag accepterar Fler detaljer