PHP Blogger

Startseite Schreib mir ne Mail! RSS Abo Webnews

Lesbaren Code schreiben

Über die Lesbarkeit von Code wird viel geschrieben. Aber trotzdem nie genug. Der PHP Blogger gibt nun sein Quentchen Weisheit dazu und hofft der Welt einen Gefallen zu tun. Nachfolgend ein paar Tipps, um Code lesbarer zu gestalten:

Gibt Bedingungen einen Namen

Jeder kennt die riesen if($prozent < $max_prozent && $prozent > $min_prozent && abs($durchschnitt_prozent - $prozent) < $durchschnitt_prozent_abweichung) - Dinger. Nach einer Woche hat man keine Ahnung mehr, was man mit diesem Code sagen wollte. Obwohl keine kryptischen Bezeichner verwendet wurden. Abhilfe? Ein Kommentar. Naja. Ich schlage mal was neues vor:

// Prozentzahl im zulässigen Bereich und keine
// größere Abweichung zum Durchschnittswert
$prozentzahl_im_zulaessigen_bereich= (
    $prozent < $max_prozent
    && $prozent > $min_prozent
    && abs($durchschnitt_prozent - $prozent)
       < $durchschnitt_prozent_abweichung
  );
if($prozentzahl_im_zulaessigen_bereich)
{
  // Mach was...
}

Cool, oder? Wenn man die selbe Bedingung oder eine erweiterte Version davon an verschiedenen Stellen benötigt, kann man es auch so machen. Und Kommentare müssen nur in speziellen Fällen überflogen werden… Ps: Schreibe auch Abbruchbedingungen für Schleifen aus! while($weitere_datenssatze_vorhanden) {}

Nutze Konstanten so oft wie möglich

Jedes Framework bietet sie an. PHP bietet sie an. Konstanten benennen Zustände oder feste Werte. Cool! Ein paar interessante Konstanten: DIRECTORY_SEPARATOR, CURRENCY_SYMBOL und THOUSANDS_SEP - Wenn das mal nicht lesbar ist…

Ein Ding ist ein Ding ist ein Ding

Benenne Objekte und Variablen nach Dingen und Zuständen und gibt Funktionen und Methoden Namen, die sich auf eine Aktion beziehen. Ein Beispiel:

define("FIRST_KEY", 1);
$haus->oeffneHaustuer(
    $schluesselbund->nimmSchluessel(FIRST_KEY)
  );

Organisiere globale Funktionen…

…obwohl sie eigenständig sind trotzdem in Hilfs-Objekten und mache sie statisch verfügbar. Ein Aufruf könnte so aussehen:

GraphicsHelper::generateThumbnail($fullsize_image);

Jedes Hilfsobjekt kommt in eine eigene Datei, die wie das Hilfsobjekt benannt ist: So findest Du Funktionsdefinitionen schneller und hast nicht eine riesige unsortierte Datei voll mit globalen Hilfsfunktionen.

Update: Verkette Funktionsaufrufe

Ein sehr mächtiges Feature ab PHP 5 ist Method-Chaining. Objekte, die von Funktionen zurückgeliefert werden, können direkt angesprochen werden: Das Ergebnis ist eine gut lesbare Funktionskette:

$app->actions(APP_CONTENT)->execute();

Method-Chaining ist nicht limitiert - wer seine Funktionen geschickt anordnet, kann fast grammatikalisch korrekte Sätze formulieren ;)

Teile und genieße Diese Icons verzweigen auf soziale Netzwerke bei denen Nutzer neue Inhalte finden und mit anderen teilen können.
  • MisterWong
  • del.icio.us
  • Technorati
  • Digg
  • Slashdot
  • YahooMyWeb
  • Furl
  • Ma.gnolia
  • Spurl
  • Netscape
  • StumbleUpon
  • MyShare
  • blogmarks

.mario meint dazu:

11. Februar 2008 um 19:10

Nicht zu vergessen: Chaining - also die Fähigkeiten von Instanzmethoden das eigen Mutterobjekt zu returnen:

$Ich->geheZumKiosk()->kaufeAirwaves()->esseDieGanzePackung(’auf einmal’);

Jann meint dazu:

11. Februar 2008 um 22:07

ja das chaining ist ja mal geil… sieht auf den ersten blick etwas performant aus, aber macht absolut sinn…

loci meint dazu:

11. Februar 2008 um 23:27

Bei Konstanten rate ich in objektorientierten Umgebungen jedoch dazu Klassenkonstanten zu nutzen, da diese zur Compilezeit ersetzt werden und nicht waehrend der Laufzeit wie gewoehnliche globale Konstanten.

Zudem hat man durch die Adressierung mit einer Klasse einen sauberen Namespace fuer seine Konstanten.

loci meint dazu:

11. Februar 2008 um 23:30

Noch ganz vergessen:
Statische aufgerufene Funktionen auch unbedingt statisch deklarieren. Sonst drohen _erhebliche_ Performanceverluste.

Ansonsten ein ganz netter Artikel. Auch wenn ich keine Variablen verschwenden wuerde um eine Bedingung lesbarer zu machen. Da verbrauchen Kommentare weniger Speicher und erfuellen den gleichen Zweck.

Nils meint dazu:

12. Februar 2008 um 09:32

Finde den Artikel auch ganz nett, aber Helperklassen sollte man wenn geht gar nicht verwenden, da sie meistens Methoden kapseln, die durch unsaubere OOP entstanden sind. Wie z.B. in deinem Beispiel leich zu sehen ist :)

timi meint dazu:

12. Februar 2008 um 12:21

Ah Mario, Method-Chaning - sehr wichtig… Habe ich gleich mal in den Artikel aufgenommen!

@loci: Da Variablen inline-stehen hast Du einen besseren Bezug zum Kontext als bei Kommentaren (die stehen ja meist eine Zeile darüber oder am Ende einer Zeile)…

@Nils: Hehe, Du Fuchs :) Ja das ist wirklich ein schlechtes Beispiel. Überlege gerade obs ein besseres gibt…

Nils Hitze meint dazu:

12. Februar 2008 um 15:15

Super Artikel Tim, danke.

freedimension meint dazu:

13. Februar 2008 um 13:42

Hi Timi
Es müsste heißen “Chaining”, mit zwei “i” ;-)
Hier geht es schließlich um Verkettung von Objekten ( http://dict.leo.org/?search=chaining ).

timi meint dazu:

13. Februar 2008 um 13:46

@free: *zwinker* der Rechtschreibfehler wurde behoben…

Sebastian meint dazu:

16. Februar 2008 um 19:00

wenn wir bei lesbaren code sind:

entscheide dich ob $duSowasSchreibst oder ob $du_sowas_schreibst und nimm das einheitlich für alles was kommt.

und zum thema call chaining: lesbarer wird der code zwar, aber debuggen (vor allem den code eines anderen) ist eine tiefe qual weil ich bei manchen funktionen zumindest eine boolche debug nachricht erhalten will. dafür muss ich aber zuerst die funktion editieren. von daher wirklich nur mit bedacht verwenden.

timi meint dazu:

17. Februar 2008 um 12:21

Hi Sebastian, meine Meinung zu Benennungskonventionen kannst Du hier nachlesen: http://www.phpblogger.net/2007/11/21/benennungs-konventionen/ und zum Debuggen: Mit einem anständigen Debugger ist Method-Chaining nicht umständlicher als eine andere Aufrufs-Verschachtelung…

Martin meint dazu:

8. März 2008 um 13:44

Ich möchte Sebastian bzgl. der Vorsicht des Chainings beipflichten. Das ist ist ja auch bei anderen Programmiersprachen beliebt, führt aber doch gerne zu Fehlern. Die beiden großen Problemfälle sind ja, dass beim Erstellen eines Objekts etwas schiefgeht, oder dass das Interface eines der Objekte geändert wurde (oder anders aussieht, als der überlastete Programmierer gerade im Kopf hat). Und wenn das dann ein Fehler ist, der einem nur ab und an mal um die Ohren fliegt, hast Du selbst mit gutem Debugger viel Arbeit. Zumindest den Fall der Null-Objekte kannst Du dann mit entflochtenen Ketten leichter entdecken.

timi meint dazu:

16. März 2008 um 11:14

Ansichtssache. Da sogar ein Standard-Debugger Function-Step-In kann (in aufgerufene Funktionen springen), kann man super schnell verführte Funktionsaustiege und somit Null-Objekte erkennen.

Im übrigen sollte man das Method-Chaining soweit im Zaumhalten, das es eben noch lesbar ist. Zu lange verkettete Aufrufe oder im schlimmsten Fall verstecke und gekapselte Kettenaufrufe machen das Debuggen auf jeden Fall zur Hölle.

RSS für Kommentare zu diesem Artikel · TrackBack URI

Schreib Deine Meinung