83 Stimmen

PHP-Codierungsstile return; in switch/case

Wir versuchen, neue Coding Style Guidelines für unser Team zu implementieren. Der php codesniffer gibt eine Warnung bei switch case Anweisungen aus, wenn kein "break" gefunden wird:

switch ($foo) {   
    case 1:
      return 1;   
    case 2:
      return 2;   
   default:
       return 3; 
}

gibt es einen guten Grund für die Verwendung von :

   switch ($foo) {
       case 1:
         return 1;
         break;
   }

Die Pause wird nie erreicht.

124voto

John Carter Punkte 52192

Es ist durchaus zulässig, die break wenn Sie return von einer switch .

Es ist jedoch gängige Praxis, explizite Angaben zu machen break s zu jedem case als defensive Programmierung üben.

switch ($foo) {
    case 1:
        return 1;
        break;

    case 2:
        return 2;
        break;
}

Die Idee ist, dass Sie bei späteren Änderungen Ihres Codes in case 1 und die Return-Anweisung entfernen, könnten Sie vergessen, eine break .

Das würde versehentlich dazu führen, dass der Programmfluss zu case 2 .

switch ($foo) {
    case 1:
        somethingDifferent();

    case 2:
        return 2;
        break;
}

Das Durchlaufen von Case-Anweisungen ist etwas ungewöhnlich, und Sie sollten einen Kommentar zu Ihrem Code hinzufügen, um zu zeigen, dass dies beabsichtigt ist.

switch ($foo) {
    case 1:
        somethingDifferentAndWeWantToDoCase2AsWell();
        // fallthrough

    case 2:
        return 2;
        break;
}

Wie bei vielen defensiven Programmierpraktiken müssen Sie abwägen, ob sich die Aufblähung des Codes - die Ihren Code möglicherweise unübersichtlich und weniger lesbar macht - lohnt oder nicht.

12voto

Chemaclass Punkte 1853

Wenn Ihr "php codesniffer gibt eine Warnung aus", versuchen Sie einen anderen, besseren Codesniffer zu bekommen und vergessen Sie nicht, die letzte stabile PHP-Version zu verwenden. Sie können natürlich auch ein break nach einem return aber es macht keinen Sinn, weil es nie gelesen wird. Ihr Code ist in Ordnung.

Sehen Sie sich das an:

$fun = function(int $argument): string {
    switch ($argument) {
        case 1:
            return "one";
        case 2:
            return "two";
        default:
            return "more than two";
    }
};
$str = $fun(4); // return "more than two"

Meiner Meinung nach ist dies einfacher und besser: weniger Zeilen => weniger zu pflegender Code :-)

8voto

James Punkte 4481

Um Ihre Frage zu beantworten: Nein, es gibt keinen guten Grund, etwas zu haben, das nichts bewirkt. Betrachten Sie es so: Ein Kommentar nach dem return anstelle einer break Die Aussage "Vergiss es nicht" hat die gleiche Wirkung - keine. Und so ausgedrückt klingt es albern, nicht wahr?

Solange Sie keine Var für eine spätere Verwendung festlegen müssen, würde ich vorschlagen, dass Ihr Ansatz völlig in Ordnung ist. Ich kannte die Absicht des Codes innerhalb von 2 Sekunden, nachdem ich ihn gesehen hatte. Mit einer break schafft nur Verwirrung.

Es gibt eigentlich keine Einheitsgröße für alle. Der richtige Ansatz hängt davon ab, was für das jeweilige Szenario passt. Setzen Sie eine Variable in jeder case und mit einer break kann der richtige Weg sein, oder vielleicht ist eine Rückkehr einfach sinnvoll.

 
 


Einige Bemerkungen zu anderen Vorschlägen, die in den Antworten gemacht wurden:

1) Ohne eine break nach return bedeutet, dass Probleme auftreten können, wenn der Code später geändert wird

Wann immer möglich, sollte der Code eindeutig, lesbar und klar sein. Wir können auch so kodieren, dass zukünftige Änderungen einfacher werden. Aber bei etwas so Einfachem wie einer switch sollte es kein Problem sein und kein Sicherheitsnetz benötigen, um eine Umstrukturierung case um später ein Element hinzuzufügen oder zu entfernen return ou break .

In der Tat, wenn Sie eine return und " Ich habe nicht bemerkt, dass es keine break ", dann ist das ein schlimmer Fehler, der in jedem Teil der Kodierung gemacht werden kann. Davor bewahrt Sie keine Überprüfung. Und man sollte sehr vorsichtig sein, wenn man für künftige Möglichkeiten kodiert, da diese Möglichkeit vielleicht nie eintritt oder etwas anderes passiert und man dann jahrelang veralteten Code pflegt.

Gleichzeitig wurde argumentiert, dass dies ein Sicherheitsnetz für künftige Änderungen sei - was, wenn man die return und versehentlich in diesem Sicherheitsnetz zurückgelassen break wenn Sie sie hätten entfernen sollen?

Selbst wenn es bei dieser Switch-Anweisung um Leben und Tod ginge und es sich um einen wirklich ernsthaften Code handeln würde, wäre ich dagegen, die "sinnlose" Pause nach dem Return einzufügen. Vergewissern Sie sich einfach, dass derjenige, der an dem Code gearbeitet hat, wusste, was er tat, und dass der Code von genügend Leuten überprüft und vollständig getestet wurde.
Wenn es so ernst wäre, dann würde man zusätzliche Kontrollen einführen, die besser sind als ein vorgeschlagenes Sicherheitsnetz, um schlampige Entwickler aufzufangen.

Wer behauptet, dass der Bruch nach der Rückkehr ein Sicherheitsnetz hinzufügt, kodiert oder testet nicht richtig. Wenn dies ein Sicherheitsnetz ist, das als nützlich erachtet wird, dann gibt es wahrscheinlich tonnenweise Fehler in dem Code an potenziell ernsteren Stellen.

Der Wiki-Artikel zur "Defensiven Programmierung" wurde verlinkt, ist aber hier nicht relevant:

Die defensive Programmierung ist eine Form des defensiven Designs, die sicherstellen soll Funktion einer Software unter unvorhergesehenen Umständen zu gewährleisten Umständen.

Hinterlassen eines Sicherheitsnetzes break in ist weder ein Szenario unvorhergesehener Umstände noch eine defensive Programmierung. Es ist einfach schlecht programmiert, und Sie können Ihren Code nicht mit Backup-Code überhäufen, nur für den Fall, dass Sie bei einer Änderung etwas nicht korrekt codieren. . Das ist ein schlechter Ansatz für die Kodierung. Das Argument, dass "wenn jemand entfernt return es nicht funktioniert", gut Sie könnte auch einen Tippfehler in der Fall var, oder vergessen, den Fall zu schreiben, oder...

En return zurückkehrt, und Sie programmieren nicht "defensiv", um zu vermeiden, dass eine Rückkehr fehlschlägt. Das würde bedeuten, dass PHP kaputt ist, und Sie werden Ihren Code nicht mit Sicherheitsnetzen ausstatten, um das zu berücksichtigen. Das ist etwas, das Sie auf einer viel höheren Ebene haben.

2) break nach return hält es explizit

Aber es ist ausdrücklich falsch. Die return zurückkehrt, so dass die Pause nicht stattfinden wird. Für mich ist das eine Zeit, in der ich mir den Kopf zerbreche und mich frage, ob ich die Absicht übersehen habe - nicht lange, denn es ist klar, was wird aber es wird einen Moment geben, in dem ich darüber nachdenke, um sicherzugehen, dass ich nichts übersehen habe.

Es ist zwar nicht ungültig oder fehlerhaft, eine return und dann break in der gleichen case ist es einfach völlig sinnlos, da die break tut nichts. Es ist sinnloser Code, der gesehen, gewartet und verstanden werden muss, da er nicht logisch ist.

Si ausdrücklich ist das zentrale Ziel y mit einer break nach einer return Wenn es Sie stört, weil es sinnlos ist, dann würde ich sagen, dass es besser wäre, eine Variable zu setzen und break und geben Sie die Variable nach Beendigung des Schalters zurück.
Wie @RageZ antworten https://stackoverflow.com/a/1437476/2632129

3) Setzen einer Variablen und Rückkehr nach Abschluss der switch-Anweisung

Gegen diesen Ansatz ist überhaupt nichts einzuwenden, aber wenn es keinen Grund gibt, den Wert in einer Variablen zu speichern (spätere Verwendung usw.), dann ist es gut, sofort zurückzukehren, wenn es keine Notwendigkeit gibt, noch etwas anderes zu tun.

Das zeigt die klare Absicht, einen Wert zurückzugeben, sobald der Fall erfüllt ist.

3voto

Lavkush Punkte 41

Ich habe viel besser solution.Please folgen unten Code für oben Schalter statment:

$result = 3; // for default case
switch ($foo) {   
    case 1:
      $result = 1;
      break;  
    case 2:
      $result = 2;
      break;    
   default:
      // do nothing
}
return $result;

Es wird zu keinem Fehler führen und der Code ist auch mit Konzepten in Ordnung.

-4voto

RageZ Punkte 25926

Ich bin kein Experte für perfekte Kodierung, aber ich denke, der Validator würde so etwas bevorzugen

switch ($foo) {   
    case 1:
      $ret =  1;   
      break;
    case 2:
      $ret = 2;
      break;   
   default:
       $ret = 3

}
return $ret

Ich denke, dass die Verwendung von Return in der Case-Anweisung, um den Codefluss zu unterbrechen, nicht wirklich eine optimale Vorgehensweise ist. Das ist der Grund, warum der Validator sagt, dass es keinen Bruch gibt ...

Was Ihre Frage nach der Kategorie angeht, so weiß ich nicht ... Entschuldigung

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X