Warum setzen C # -Entwickler Zeilenumbrüche in Klammern? [geschlossen]

44

Ich habe in den letzten Jahren hauptsächlich mit C # und SQL gearbeitet. Jeder Programmierer, mit dem ich in dieser Zeit zusammengearbeitet habe, pflegte die öffnende Klammer einer Funktions- oder Kontrollflussanweisung in eine neue Zeile zu setzen. Damit ...

public void MyFunction(string myArgument)
{
     //do stuff
}

if(myBoolean == true)
{
    //do something
}
else
{
    //do something else
}

Es hat mich immer beeindruckt, wie viel Platz verschwendet wird, insbesondere bei if / else-Anweisungen. Und ich weiß, dass es in späteren Versionen von C # Alternativen gibt, wie zum Beispiel:

if(myBoolean == true)
    //do something on one line of code

Aber kaum jemand hat sie benutzt. Alle machten die Sache mit der geschweiften Klammer auf der Newline.

Dann habe ich mich nach langer Abwesenheit wieder mit JavaScript beschäftigt. In meinem Gedächtnis haben JavaScript-Entwickler früher genau dasselbe getan wie geschweifte Klammern und Zeilenumbrüche, aber mit all den schick neuen Bibliotheken und Dingen haben die meisten Entwickler die öffnende Klammer nach der Deklaration eingefügt:

function MyJavaScriptFunction() {
    //do something
}

Sie können den Sinn daran erkennen, dass die Verwendung von Closures und Funktionszeigern in JavaScript populär geworden ist. Dadurch wird viel Platz gespart und die Lesbarkeit verbessert. Also fragte ich mich, warum es in C # nicht als erledigt angesehen wurde. Wenn Sie das obige Konstrukt in Visual Studio 2013 ausprobieren, wird es tatsächlich für Sie neu formatiert und die öffnende Klammer in eine neue Zeile gesetzt!

Jetzt habe ich diese Frage in Code Review SE gesehen: https://codereview.stackexchange.com/questions/48035/questions-responses-let-me-tell-you-about-you In dem ich das in Java gelernt habe, a Sprache, mit der ich nicht allzu vertraut bin. Es wird als hinderlich angesehen, die geschweiften Klammern direkt nach der Deklaration in moderner JavaScript-Form zu öffnen.

Ich hatte immer verstanden, dass C # ursprünglich Java nachgebildet war und viele der gleichen basalen Codierungsstandards einhielt. Aber in diesem Fall scheint es nicht. Ich nehme also an, dass es einen guten Grund geben muss: Was ist der Grund? Warum erzwingen C # -Entwickler (und Visual Studio) das Öffnen von geschweiften Klammern in einer neuen Zeile?

Bob Tway
quelle
30
Konvention ist einfach das.
Oded
19
Visual Studio erzwingt nichts, der Codestil ist konfigurierbar. Etwas muss der Standard sein. Welcher Standard "besser" ist, ist Bikeshedding auf höchstem Niveau.
Phoshi
23
Die Klammer am Ende der Linie entspricht dem alten K & R C-Standard. Kernighan und Ritchie erfanden die C-Sprache, wenn Computeranzeigen nur 25 Zeilen hatten (23, wenn Sie Kopf- und Statuszeilen hinzufügen). Das ist doch nicht mehr so, oder? Wichtig ist die Konsistenz im gesamten Projekt. Es gibt auch wissenschaftliche Studien , die zeigen , dass die Klammer in einer eigenen Zeile (eingekerbt auf dem gleichen Niveau wie der Code in der Tat) verbessert Code Verständnis trotz allem , was die Menschen denken , dass sie von der Ästhetik denken.
Craig
10
C # hat es übrigens immer unterstützt, eine einzelne Codezeile nach einer Bedingung auszuwerten. Tatsächlich ist das das einzige, was es auch jetzt noch tut. Wenn Sie den Code nach einem Verzweigungsausdruck in geschweifte Klammern setzen, wird diese Anweisung nur zu einem goto (der Compiler erstellt den Gültigkeitsbereich mithilfe von jmp-Anweisungen). C ++, Java, C # und JavaScript basieren größtenteils mehr oder weniger auf C mit denselben zugrunde liegenden Analyseregeln. In diesem Sinne basiert C # nicht auf Java.
Craig
10
Als Randnotiz if(myBoolean == true)ergibt das für mich wenig Sinn. Während wir dabei sind, während nicht if ((myBoolean == true) == true)? Nur if (myBoolean)und das ist genug. Tut mir leid, mein Haustier.
Konrad Morawski

Antworten:

67

Die Klammer am Ende der Zeile ist der alte K & R C-Standard aus Brian Kernighans und Dennis Ritchies Buch The C Programming Language , das sie 1978 veröffentlichten, nachdem sie das UNIX-Betriebssystem und die C-Programmiersprache miterfunden hatten (ich glaube, C war es) meist von Ritchie entworfen), bei AT & T.

Früher gab es Flammenkriege um "den einen wahren Zahnspangenstil".

Ritchie erfand die C-Sprache und Kernighan schrieb das erste Tutorial, in dem Computerbildschirme nur wenige Textzeilen zeigten. Tatsächlich begann die Entwicklung von UNICS (später UNIX) auf einem DEC PDP-7, der eine Schreibmaschine, einen Drucker und ein Papierband als Benutzeroberfläche verwendete. UNIX und C wurden auf dem PDP-11 mit 24-Zeilen-Textterminals fertiggestellt. Der vertikale Raum war also in der Tat sehr knapp. Wir haben heute alle etwas bessere Displays und Drucker mit höherer Auflösung, oder? Ich meine, ich weiß nichts über dich, aber ich habe gerade drei (3) 24 "1080p-Displays vor mir. :-)

Außerdem handelt es sich bei so viel von diesem kleinen Buch, The C Programming Language, um Codebeispiele, bei denen die geschweiften Klammern an den Zeilenenden und nicht in den eigenen Zeilen angebracht wurden. Dies sparte angeblich eine beträchtliche Menge Geld beim Drucken.

Was wirklich wichtig ist, ist die Konsistenz während eines Projekts oder zumindest innerhalb einer bestimmten Quellcodedatei.

Es gibt auch wissenschaftliche Studien, die belegen, dass die geschweifte Klammer in einer eigenen Zeile (die tatsächlich auf der gleichen Ebene eingerückt ist wie der Code) das Codeverständnis verbessert, ungeachtet dessen, was die Leute von der Ästhetik halten. Es macht dem Leser visuell und instinktiv sehr deutlich, welcher Code in welchem ​​Kontext abläuft.

if( true )
    {
    // do some stuff
    }

C # hat es übrigens immer unterstützt, einen einzelnen Befehl nach einem Verzweigungsausdruck auszuwerten. Tatsächlich ist das das einzige, was es auch jetzt noch tut. Wenn Sie den Code nach einem Verzweigungsausdruck in geschweifte Klammern setzen, wird dieser Befehl nur zu einem Goto (der Compiler erstellt den Gültigkeitsbereich mithilfe von JMP-Anweisungen). C ++, Java, C # und JavaScript basieren größtenteils mehr oder weniger auf C mit denselben zugrunde liegenden Analyseregeln. In diesem Sinne basiert C # nicht auf Java.

Zusammengefasst, das ist ein bisschen eine religiöse / flame-war Thema. Es gibt jedoch Studien, die ziemlich deutlich machen, dass die Anordnung von Code in Blöcken das menschliche Verständnis verbessert . Dem Compiler ist das egal. Dies hängt aber auch damit zusammen, warum ich nach einer Verzweigung ohne geschweifte Klammern nie eine Codezeile einfüge - für mich oder einen anderen Programmierer ist es einfach zu einfach, später eine andere Codezeile einzufügen und darauf hinzuweisen, dass dies nicht der Fall ist im selben Kontext mit der Zeile direkt davor oder danach ausführen.

BEARBEITEN : Schauen Sie sich einfach den Apple- goto failFehler an, um ein perfektes Beispiel für genau dieses Problem zu finden, das schwerwiegende Konsequenzen für die reale Welt hatte.

if( true )
    doSomething();

wird...

if( true )
    doSomething();
    doSomethingElse();

doSomethingElse()Wird in diesem Fall immer ausgeführt, unabhängig vom Ergebnis des Tests. Da es jedoch auf der gleichen Ebene eingerückt ist wie die doSomething()Anweisung, kann es leicht übersehen werden. Das ist nicht wirklich fraglich. Studien belegen dies. Dies ist eine große Quelle von Fehlern, die während der Wartung in den Quellcode eingedrungen sind.

Trotzdem gebe ich zu, dass die JavaScript-Schließungssyntax mit geschweiften Klammern in ihren eigenen Zeilen ein wenig albern aussieht ... ästhetisch. :-)

Craig
quelle
13
Der Teil über Blöcke in Bedingungen ist leicht irreführend. In C hat die Bedingung immer eine einzelne Anweisung, aber ein Block (auch zusammengesetzte Anweisung genannt) ist eine Art Anweisung . C # folgt diesem Präzedenzfall. Auf jeden Fall impliziert die bedingte Auswertung immer eine Art bedingte Sprung- oder Verzweigungsanweisung, da alle gängigen Befehlssätze linear sind. Eine Bedingung ohne Block unterscheidet sich qualitativ nicht von einer Bedingung mit Block (mit Ausnahme des Gültigkeitsbereichs).
Amon
3
@Craig, denk dran, das war bei Bell Labs, als Bell Labs gechartert wurde, um "interessante Sachen zu machen", die für nichts unbedingt praktisch sein mussten. Bringen Sie kluge Leute in ein Gebäude, fordern Sie sie auf, interessante Nachforschungen anzustellen, sie aus dem herauszuholen, was sie nicht "interessant" machen, und, komischerweise, neigen interessante Dinge (wie Transistoren und Unix) zum Herausplatzen. DARPA hatte zu Beginn einen ähnlichen Schwerpunkt und finanzierte im Namen der Grundlagenforschung eine Menge gute Arbeit.
John R. Strohm
3
@Craig: In den alten Pascal / Delphi-Tagen habe ich es normalerweise für einzeilige Blöcke vermieden, wie Pascal sie verwendet, beginund endanstelle von geschweiften Klammern, was solche Fehler wirklich schwer zu übersehen macht, und es auch strenger in Bezug auf die Semikolon-Platzierung - aber mit Ausgaben 4 Tage im letzten Jahr, um ein Problem in Embedded C zu beheben, das letztendlich auf die fehlende Platzierung von geschweiften Klammern zurückzuführen war ..... Ich denke, es sollte eine Compiler-Option geben, die geschweifte Klammern für Steueranweisungen obligatorisch macht!
Mark K Cowan
12
Bitte geben Sie Hinweise für "... wissenschaftliche Studien, die belegen, dass die Zahnspange auf einer eigenen Linie steht ...". Ohne mindestens zwei Referenzen (sonst wäre es Studie , nicht Studien ), schießt es nur zufällig in die Luft.
ErikE
2
@Craig, könnten Sie einige Hinweise geben, wie Sie die von Ihnen erwähnten Forschungsstudien finden können?
Grzegorz Adam Kowalski
30

Der Grund, warum C # -Entwickler dies tun, liegt darin, dass dies die Standardeinstellung des automatischen Formatierungsprogramms von Visual Studio ist. Diese Einstellung kann zwar geändert werden, die meisten Benutzer tun dies jedoch nicht. Daher müssen sich alle Entwickler in einem Team der Mehrheit anschließen.

Warum dies der Standard in Visual Studio ist, weiß ich nicht.

Timwi
quelle
15
Dies ist die Standardeinstellung in Visual Studio, da es sich bei Microsoft seit jeher um den allgemein akzeptierten Codierungsstil handelte. Tatsächlich bestand der Stil in einigen Teams von Microsoft nicht nur aus geschweiften Klammern in den eigenen Zeilen, sondern auch aus geschweiften Klammern in den eigenen Zeilen und eingerückt. Das ist auch eine Option in Visual Studio (ich persönlich bevorzuge es).
Craig
20
@Craig: Ewwwwwwwww
Leichtigkeit Rennen mit Monica
5
@PreferenceBean Hmm. Persönlich mag ich den K & R-Stil nicht, weil die Klammern nur am Ende der Zeilen geräuschlos sind und der Text für mich klumpig aussieht, was nicht nur eine ästhetische Vorliebe ist, sondern einen tatsächlichen Einfluss auf die Lesbarkeit / das Verständnis hat. Ich mag vertikale Leerzeichen. Auf 12 "-Monitoren mit 24 Textzeilen war es früher etwas anders, als vertikaler Raum kostbar war.
Craig
10
@Craig: Das ist keine Entschuldigung für das Einrücken der Klammern: P
Lightness Races mit Monica
2
@Craig Um Microsoft-Mitarbeiter unglücklich zu machen?
Mateen Ulhaq
18

Wie ich in dieser Antwort hier vermutet habe - https://softwareengineering.stackexchange.com/a/159081/29029 -, könnte die Entscheidung, sich für Allman zu entscheiden, ein Zeichen der Pascal-Tradition sein, da Hejlsberg Delphi vor seinem Entwurf von C # erstellt hat. . Entspricht dem Pascal-Fall für Methodennamen.

Persönlich glaube ich daran, dem Sprichwort "in Rom zu tun, wie es die Römer tun" zu folgen. Ich verwende Allmans in C #, aber K & R in Java. Ich bin so daran gewöhnt, dass es mich nervt, die Konvention so oder so zu wechseln.

Ich bin der Meinung, dass eine gewisse Konventionsvielfalt für einen "mehrsprachigen" Entwickler tatsächlich von Vorteil ist, da er sich leichter merken kann, in welcher Sprache er gerade programmiert und verschiedene Gewohnheiten leicht unterscheiden kann. Es ist sozusagen ein mentales Äquivalent zum Muskelgedächtnis.

Konrad Morawski
quelle
7
Tatsächlich +1 für die Zeile "Multilanguage Developer". Ich bevorzuge ernsthaft Klammern in ihren eigenen Linien und eingerückt. Bei der Arbeit an beispielsweise ASP.NET (MVC) -Projekten finde ich jedoch, dass mir C # mit dem "richtigen" Stil und JavaScript mit dem "JavaScript" -Stil gefallen. Das ist ein kleines Augenzwinkern, aber ehrlich gesagt ist es ein Teil davon, dass die Schließungssyntax von JavaScript mit der Klammer am Ende der Zeile attraktiver ist. Ich bin also genauso ein Sklave der Ästhetik wie jeder andere ...
Craig
PascalCase für Methodennamen war lange Zeit ein Standard bei Microsoft, bevor Anders Hejlsberg Borland verließ, um ein angesehener Software-Ingenieur bei Microsoft zu werden.
Craig
2
Interessanterweise benutze ich Allman für alle Klammer-Block-Sprachen. Ich bin jedoch zunehmend daran interessiert, wie eine Vorverarbeitungskonvertierung von Einzügen in geschweifte Klammern in Java aussehen könnte. Der "Java" -Code sieht möglicherweise sehr sauber aus, wenn ich ihn erst einmal mit meinem Mustererkennungsgedanken umwickelt habe. Ich denke, Python könnte es tatsächlich richtig machen: Es gibt wirklich keinen guten Grund für geschweifte Klammern in einer Sprache.
tgm1024
Das Verwenden von Leerzeichen zur Steuerung des Programmflusses ist Wahnsinn. Python ist heutzutage sehr beliebt, aber dieser Aspekt von Python war ein bisschen verrückt, seit er zum ersten Mal aufgetaucht ist.
Craig
@Craig Python-Fan hier, versucht, etwas in Javascript zu erledigen. Wenn Sie sich Ihre andere Antwort und Ihre Bearbeitung goto failansehen, ist die Verwendung des Einzugs zur Steuerung des Programmflusses das, was Menschen natürlich tun möchten. Was Sie also sehen, ist das, was ausgeführt wird. Wenn es falsch eingerückt ist, funktioniert es nicht. Zu dekodieren, was diese Klammern bedeuten, ob sie tatsächlich den Einzug widerspiegeln, ist zusätzliche Arbeit, die über das Verstehen des Programms hinausgeht. Einrückung ist für geschweifte Klammern überflüssig. Warum wird sie von Programmierern verwendet, wenn die geschweiften Klammern nützlich sind? Deep Nesting ist in keiner Sprache verständlich. Jus 'sayin'.
Neil_UK
14

Die Konvention , dass Sie mit Java verbinden ist der K & R - Stil, oder der „einzig wahre Stütze Stil“ und stammt ursprünglich aus C. Dieser Seite indent-Stil aus der altehrwürdigen Jargon File zeigt , wie alt die Unterscheidung ist.

Ich habe immer gedacht, dass der Allman-Stil und seine Varianten die Einstellung der Autoren zum Code widerspiegeln und die Blocktrennzeichen auf die Ebene von Schlüsselwörtern heben, ähnlich wie einige Sprachen "Anfang" und "Ende" um Codeblöcke verwenden.

John Bickers
quelle
Ich habe den Eindruck, dass heutzutage OTBS (ein echter Klammerstil) auch impliziert, dass die Klammern nach Steueranweisungen nie weggelassen werden, auch nicht für einzelne Codezeilen. Schauen Sie sich den Apple Goto Fail Bug an.
Craig