Konventionen für Source Code

Bekanntlich wird ja Code viel öfter gelesen als geschrieben. Meistens natürlich auch noch von unterschiedlichen Personen. Darum ist es äußerst wichtig, dass der Quelltext leserlich, leicht verständlich und damit auch einfach wartbar ist.

Das setzt natürlich einen exzellenten Schreibstil voraus. Und in einer Gruppe von drei Programmieren wird man vermutlich auch drei verschiedene Meinungen finden, wie den jetzt guter Stil genau aussieht. Hält sich jeder an seinen eigenen guten Stil, wird das Endprodukt, an dem alle gemeinsam arbeiten, vermutlich zum Fleckerlteppich. Das kann schon bei trivialen Dingen wie der Benennung von Variablen zum Problem werden:

Willi verwendet seit Jahren die hungarian notation und seine Variablen haben auch englische Namen.
Deshalb definiert er eine seiner Variablen so:

 //changeFlag
int m_iAlter; 

Für ihn ist ganz klar was gemeint ist: Er sieht sofort den Gültigkeitsbereich und den Typ. Speichern will er in dieser Variable den Status, ob sich die Klasse geändert hat. Ganz klar für ihn, er macht das immer so.

Norman findet Abkürzungen super. Deshalb würde er die selbe Variable so definieren:

 boolean chgd;

Josef hingegen liebt ausgeschriebene Variablen und entwickelt grundsätzlich in Deutsch. Sein Code:

 boolean ObjektIstUnverändert; //Wird falsch wenn jemand das Objekt modifiziert

Jetzt hat man mit einem simplen Beispiel drei komplett unterschiedliche Ausprägungen. Und das bei nur einer einzigen Zeile Code. Ganz klar, dass hier schwer lesbarer und unwartbarer Code entsteht. Um das zu vermeiden, muss man sich auf einen gemeinsamen Stil einigen.

Doch was sollen jetzt diese Code Conventions alles abdecken?

  • Naming:
    Wie benennen wir Variablen/Konstanten/Klassen/Typen/Namespaces …? In welcher Sprache? Was schreiben wir groß, was klein?
    Was machen wir mit Sonderzeichen?
  • Kommentierung:
    Was kommentieren wir, wo und in welcher Detailstufe?
  • Klammernsetzung und Einrückung:
    Wohin setzen wir bei Kontrollstrukturen die Klammern hin? Folgezeile? Wie tief rücken wir wann ein?
  • Verbote ?:
    Gibt es Language Features die wir explizit vermeiden wollen (goto, globale Variablen ..) ?
  • Best Practices:
    Maximale Zeilenanzahl von Funktionen und Klassen, Obergrenze der Anzahl von Übergabeparametern einer Funktion, Hardcodierung von Werten …

Als erstes hilft es sicherlich, sich an Herstellervorgaben zu orientieren, wie bei Java, .net oder python. Ich würde hier nur bei Sonderfällen von diesen Vorgaben abweichen, weil sie defacto Standards sind. Von diesen kann man seine internen Konventionen ableiten und mit Best Practices anreichern.

Wichtig ist aber auch, dass die Konventionen nicht zu umfangreich werden. Ein dickes “Gesetzbuch” wird wohl niemand lesen, kennen und einhalten. Hier helfen kleine Codebrocken viel mehr als Beschreibungen in Prosa. Wirklich gut gelungen finde ich den IDesign C# Coding Standard.

Aber am wichtigsten ist natürlich die Einhaltung solcher Conventions. Sonst macht das keinen Sinn.

Produktiver arbeiten mit Cygwin

Am meisten unter Windows fehlt mir mit Abstand eine brauchbare Command-line. Microsoft hat zwar vor einiger Zeit mit der Powershell hier nachgebessert, trotzdem wurde und werde ich damit nicht richtig warm. Das liegt aber vermutlich auch sehr daran, dass ich vermehrt auf unix-artigen Systemen arbeite. Dort hat sich de facto die bash als Standard etabliert. Dank cygwin kann man auch unter Windows mit der bash arbeiten.

Cygwin ist einerseits nicht mehr als eine dll, die Unix System Calls in die Windows-Welt “übersetzt”. Mit dieser Emulationsschicht wird es viel einfacher, Unix Programme unter Windows zum Laufen zu bringen.
Den zweiten Teil von cygwin bilden die eigentlichen Programme, die man mit dem mitgelieferten Setup relativ einfach selektieren, installieren und  updaten kann.

In der Praxis ist die Einrichtung von cygwin ziemlich easy: Man lädt sich die aktuelle setup.exe auf der cygwin-Seite herunter und führt sie aus.
Im Setup kann man optional zusätzliche Pakete/Programme sofort mit-installieren, per default ist die minimum Base selektiert, die für den ersten Start schon mal reicht. Für ein späteres Update oder zum Installieren von zusätzlichen Programmen startet man einfach das Setup neu.

Ist die Installation durch, kann man schon cygwin und damit die bash starten:

Grundsätzlich funktionert jetzt schon alles, trotzdem sollte man dem Standard – Terminalprogramm bessere Umsetzungen vorziehen:

Zum einen gibt es puttycyg, eine gepatchte Version von putty, mit der man auch auf das lokale cygwin zugreifen kann.

Ich verwende aber mintty als Terminal, weil es sich besser in Windows integriert, copy/paste entscheidend besser funktioniert und weil es viel mehr Einstellungen bietet. Mintty kann man einfach im setup.exe auswählen, es wird danach ein Eintrag im Startmenü angelegt.

Wenn man jetzt noch weiß, dass man auf das Windows C: Laufwerk im cygwin unter cygdrivec findet, hat man endgültig gewonnen und kann endlich mit der bash und den Standard Unix Tools unter Windows arbeiten. Zumindest ich bin dadurch um Welten produktiver.

Kuh vs. Erdmännchen

Vor etwas mehr als zwei Jahren habe ich einen Artikel geschrieben über meine Erfahrungen mit Gentoo Linux. Seit dieser Zeit hat sich doch das Eine oder Andere geändert.

Gleich geblieben ist definitiv meine Freude mit Linux. Allerdings tue ich mir nicht mehr die Arbeit mit Gentoo an. Ich will nicht immer wieder selber kompilieren, bei den Updates die Config-Files per Hand mergen. Generell will ich mit Updates so wenig Arbeit wie möglich haben. Das soll einfach funktionieren. Automatisch am Besten.

Irgendwann bin ich dann bei Ubuntu angelangt und bin bis jetzt äußerst zufrieden. Ubuntu gefällt mir wegen der Einfachheit, es funktioniert eigentlich problemlos. Die Zeiten, wo man noch verdammt viel wissen musste, um sich ein Linux zu installieren, sind lange schon vorbei. Das geht mindestens so einfach wie bei Windows. Und wenn man dann doch mal ansteht, gibt es eine Doku, die ihresgleichen sucht.

Ganz besonders gefällt mir die Paketverwaltung in Ubuntu. Neue Programme werden aus definierten Katalogen geladen und dann installiert und konfiguriert. Über diesen Katalog sind auch Updates zu den bereits installierten Programmen abgreifbar. Ubuntu weiß welche Programme in welchen Versionen installiert wurden und kann somit periodisch alle diese Anwendungen auf mögliche Aktualisierungen prüfen. Dieses Konzept fehlt mir bei Windows und am Mac komplett, hier ist jedes Programm auf sich selbst gestellt. Eine vollständige Systemaktualisierung gibt es da so einfach nicht. Bei Ubuntu (eigentlich generell bei Linux) ist das aber der Usus.

Meinen Mac verwende ich nur mehr wegen meiner iPhoto – Familienfotosammlung und wegen iTunes. Windows brauche ich privat nur ganz selten, und wenn, dann nur zum Spielen. Wobei da ist mir mittlerweile die PS3 auch schon lieber. Vor zwei Jahren machte mir noch das Entwickeln unter Windows Spaß. Mittlerweile ist das schon längst nicht mehr so. Um auf einem Windows Rechner richtig produktiv zu sein, brauche ich cygwin, das mir ein Linux emuliert. Nur so fühle ich mich halbwegs zuhause, aber halt emuliert.

Aber natürlich gibt es auch nicht so tolle Seiten an Ubuntu. Mir fehlt beispielsweise ein anständiges Grafikprogramm. Auch bei der Navigation im System-menü habe ich so meine Schwierigkeiten, weil ich auf den ersten Klick nie das Gesuchte finde.

Aber eigentlich wird ja das Betriebssystem immer unwichtiger. Wichtiger wird dagegen immer mehr ein Programm, in dem die meisten weiteren Anwendungen laufen. Ein Container, den ich eigentlich immer offen habe und der mehr und mehr das eigentliche Betriebssystem ablöst. Klar, ich rede vom Browser. Aber das ist eine andere Geschichte…