Refactoring Patterns #1 Guard Clause

Ähnliche Inhalte

Refactoring Patterns #1 - Guard Clause

Software ist niemals fertig. Es kommen neue Funktionen dazu, oder der Code wird an veränderte Bedinungen angepasst. Um ein Projekt über viele Jahre wartbar zu halten und anderen Entwicklern es zu erleichtern sich in den Code einzuarbeiten ist es gut, wenn dieser einfach zu verstehen ist.

Dazu gehört, dass Klassen und Methoden kurz und einfach verständlich sind. Ebenso sollte durch gut Namen erkennbar sein, was eine Klasse oder Methode tut, oder welchen Wert eine Variable haben kann.

Manchmal ist es leider so, dass der vorhandene Code nicht leicht zu verstehen ist. Über viele Jahre sind Klassen und Methoden gewachsen. Änderungen am Code dauern lange und nur ungerne werden diese gemacht.

Höchste Zeit etwas daran zu ändern... In diesem und weiteren Post möchte ich Muster aufzeigen, die eine schwer verständliche Codestruktur zeigen. Ausserm möchte an Beispiel zeigen, wie man diese Struktur Schritt für Schritt verbessen kann.

 

Verschachtelte If/Else-Strukturen

class Calculator {
    /**
    * Calculates the sum of all items with an odd key in the array.
    *
    * @param array $items
    * @return float 
    */
    public function getSumOfOddItems($items) {
         $sum = 0;
         if(is_array($items)) {
             foreach($items as $key => $itemValue) {
                 if(is_numeric($itemValue)) {
                     if(($key % 2) === 1) {
                         $sum += $itemValue;
                     }
                 }                  
             }
         }
         return $sum;
    }
}

Das obere Beispiel berechnet die Summer aller Element eines Arrays, die einen ungeraden Schlüssel haben. Wie man sieht ist die Struktur ein bisschen verschachtelt. Es wird erst geprüft ob der übergebene Wert ein Array ist. Erst dann wird eine Schleife durchlaufen für alle Elemente. In der Schleife wird geprüft, ob der Werte eine Zahl ist und ob der Key ungerade ist.

Durch die vielen If Blöcke ist die Struktur sehr tief geschachtelt.

Frühe Rückgabe mit Guard Clausing

Doch wie geht es besser?  Wir wissen, dass die Summe 0 sein muss, wenn der übergebene Wert kein Array ist. Ausserdem können wir in der Schleife die Werte überspringen, die keine Zahl sind, oder die einen geraden Key haben.

Wir geben also am Anfang der Methode schon einen Wert zurück, wenn wir nicht mehr weiter machen müssen und überspringen ein Element, wenn wir wissen, dass wir damit nicht weitermachen müssen.

 

class Calculator {
    /**
    * Calculates the sum of all items with an odd key in the array.
    *
    * @param array $items
    * @return float 
    */
    public function getSumOfOddItems($items) {
         $sum = 0;
         if(!is_array($items)) {
             return $sum;
         }
         foreach($items as $key => $itemValue) {
             if(($key % 2) === 0) continue;
             if(!is_numeric($itemValue)) continue;

             $sum += $itemValue;
         }
         return $sum;
    }
}

Wenn man sich das Beispiel oben anschaut, so ist das berechnet Ergebnis das gleiche. Jedoch ist die Verschachtelungstiefe in der zweiten Variante maximal 2 Ebenen während sie in der ersten Varianten 4 Ebenen ist.

Mögliche Codestellen für Guard Clauses finden und umschreiben

Bevor bestehender Code angepasst wird, macht es Sinn diesen automatisiert mittels Unittest zu testen. Dadurch kann sichergestellt werden, das eine Änderung die alte Funktionalität nicht kaputt macht.

Stellen im Code, die durch Guard Clausing optimiert werden kann erkennt man klassischerweise daran das:

  • Es mehrere verschachtelte Ebenen mit Schleifen und If/Else Stukturen gibt.
  • Es nur am Ende der Methode eine Rückgabe (return) gibt.

Oftmals, wie auch im Beispiel oben kann eine Bedigung in der If-Anweisung negiert werden und dann innerhalb des If ein return gemacht werden (siehe Zeile 10-12).

Das obere Beispiel kann im Ansatz zeigen, warum Guard Clauses sinnvoll sein können. In realten gewachsenen Applikationen findet man oft schnell längere Beispiel die in der Lesbarkeit verbessert werden können.

Viel Spaß beim Suchen und optimieren!

Navigation