Kategorie: Informatik

Restklassenringe

Im ersten Semester lernt man im Informatikstudium Restklassenringe kennen. Diese bilden die mathematische Basis für diverse Kryptographie (beispielsweise RSA), aber auch anderes Zeug wie CRC. Gestern hatte ich im Forum mal ne oberflächliche Einführung in das Thema gegeben. Und damit das nicht verloren geht, will ich das hier nochmal posten. Wer also kein Informatik studiert, aber aus welchen Gründen auch immer wissen will, was modulare Arithmetik ist und wie man in Restklassenringen rechnet, hier eine knappe Einführung. weiter lesen »

Agile: Wenn “agil” draufsteht…

… ist wohl nicht immer agil drin.

Dilbert.com

Leider wird Agile Softwareentwicklung oft so verstanden, wie in obigem nicht nur einmal zitiertem Dilbert-Comic. Mein Eindruck ist manchmal, dass das Wort “agil” dazu benutzt wird, dem Nichtvorhandensein einer strukturierten und durchdachten Vorgehensweise einen Namen zu geben. Aber genau das ist agile Softwareentwicklung eben *nicht*. Agile Softwareentwicklung heißt nicht einfach mal drauflos coden und hoffen, dass alles schon irgendwie gut geht.

Letztens hab ich auf heise eine interessante Umfrage gesehen, die genau das zeigt. Zumindest ist das meine Interpretation der Daten.

Nach der Umfrage nutzen 17% gar kein Vorgehensmodell. Dazu kommen die oben genannten Feigenblatt-Agilen und wohl auch ein paar Feigenblatt-Phasenorientierten. Wenn man jetzt auch noch bedenkt, wer die Fragen beantwortet hat (Tester, Entwickler, Manager, …), dann zeigt sich, dass Entwickler deutlich häufiger angeben, keinem Vorgehensmodell zu folgen. Da aber wohl die Entwickler diejenigen sind, die das am besten wissen sollten, vermute ich mal, dass die 26% (Entwickler, die angegeben haben, keinem Vorgehensmodell zu folgen) eher stimmen als die 17% (Durchschnitt über alle Rollen). Da klaffen wohl Anspruch und Wirklichkeit etwas auseinander.

Aber gucken wir mal genauer:

  • 27% der “agilen” nutzen ein “eigenes agiles Vorgehensmodell”. Soso…
  • 57% nutzen Scrum (weil es grad in Mode ist, das zu behaupten)
  • Nur bei 43% der “agilen” Projekten sind Unit-Tests vollständig automatisiert. Knapp 30% haben eine Automatisierungsquote unter 70%. Und nennen sich dabei “agil”.

Die genannte Statistik hat sich jetzt auf Tests konzentriert. Ich schätze mal, wenn man da in andere Richtungen fragt, wird man ein ähnliches Bild erhalten: Nicht alle, die behaupten, agile Softwareentwicklung zu betreiben, tun das auch.

Pi mal Daumen schätze ich also mal, ein Drittel der agilen sind nicht wirklich agil. Grob geraten sind wohl 50% phasenorientiert 20% agil und 30% gar nix. Und die Übergänge sind fließend.

Teilweise herrscht auch ein falsches Verständnis: Auf ner Firmenkontaktmesse hab ich auch mal gehört, “agil” sei ja gar nicht neu; früher nannte man das nur iterativ. Aber so ist es natürlich nicht. Die Aussage ist in etwa genauso richtig, wie zu behaupten, dass früher (“prozedural”) Klassen einfach structs oder records geheißen haben. Technisch mag das bis zu einem gewissen Grad stimmen (aber auch nur zum Teil). Jedoch hat sich die Denkweise geändert. Und die Denkweise ist es, die den großen Unterschied macht — sowohl bei der Objektorientierung alsauch bei der agilen Softwareentwicklung.

Nichtsdestotrotz gibt es auch Firmen, die Agilität richtig verstehen und richtig anwenden. Durch die ein oder andere Exkursion hab ich da auch schon welche kennen lernen dürfen. Effektiv ist in den meisten Firmen, die ich bisher kennen gelernt habe, Agilität zumindest ein Thema. Ich denke, man kann also behaupten Agile Softwareentwicklung ist mittlerweile im Mainstream angekommen. Nur heißt das eben noch nicht, dass alle, die sich “agil” nennen, das auch sind.

Warum manchmal unerklärliche Dinge geschehen

“Schon traurig, dass von mir als Informatiker manchmal als einziger Lösungsvorschlag ‘Stecker ziehen und wieder reinstecken’ kommt. — Und noch trauriger ist es, dass das auch noch hilft.”

Manchmal passieren Dinge, die uns unerklärlich, ja unglaublich erscheinen. In den letzten paar Tagen, durfte ich an ein paar WLANs rumbasteln und dabei sind diverse solcher Dinge passiert. Und das hat mich dann dazu gebracht, obiges zu meinem Cousin zu sagen. Das will ich mal zum Anlass nehmen und etwas darüber sagen, wie diese unerklärlichen Dinge geschehen.

Aber was ist denn nun passiert?

  • Der neue WLAN-Router tut nicht so, wie er soll. Zuerst kommt er ins Internet, aber das WLAN geht nicht. Dann geht WLAN aber kein Internet mehr. Nach ein paar mal neu Booten und Stecker ziehen und wieder reinstecken, tut es wieder.
  • Ein anderer WLAN-Router (gleiches Modell) hat laut LED eine Verbindung mit dem Internet. Das Kabel steckt aber nicht im WAN-Port. Netzstecker ziehen und wieder reinstecken und es geht.
  • Der selbe WLAN-Router ist per Ping zu erreichen, zeigt bei Eingabe der IP in den Browser keine Konfigurationsoberfläche (Timeout). Ein Reset behebt das Problem.
  • Bei selben Gerät ein Admin-Passwort eingerichtet (händisch in beide Edit-Felder eingetragen und gespeichert). Danach nimmt er das Passwort beim Anmelden aber nicht mehr an. Nach einem Reset nochmal versucht (diesmal langsam eingetippt). Selbes Problem. Dann Dummy-Passwort “abc” zum Probieren. Lustigerweise funktioniert das jetzt. Dann das Wunsch-Passwort nicht eingetippt, sondern per Copy’n'Paste jeweils eingefügt. Wieder “Benutzername oder Kennwort falsch”.
  • Einen WLAN-AccessPoint als Repeater konfiguriert. Datendurchsatz ca. 40kbps (ja 40kbps bei 802.11n und ner Entfernung von 20cm). Neu Starten hilft diesmal nicht. Zum Testen als AP-Client konfiguriert: selbes Problem. Zum Testen mit anderem AccessPoint verbunden: Klappt problemlos. Wieder zurück zum eigentlich gewünschten AccessPoint: Wieder ewig lahm. Neu Starten hilft immer noch nicht. Einen Tag später nochmal versucht: Klappt auf Anhieb.
  • Bei Verwendung des neues Repeaters friert der Rechner ein (Maus und Tastatur reagieren nicht mehr). Der Rechner war per Ethernet-Kabel mit dem Repeater verbunden. Selbst nach Abziehen des Kabels (also der Rechner ist mit dem Repeater nicht mehr verbunden. Beide stehen nur nebeneinander) besteht das Problem weiterhin. Ein bisschen WLAN lässt den Rechner einfrieren.
  • Auch ein DSL-Router war mal per Ping zu erreichen und per Browser nicht. Wieder behob ein Steckerziehen das Problem.

Aber wie kann das alles sein? Und was hat das mit Software-Entwicklung zu tun? Ich wage mich mal an eine Erklärung des Unerklärlichen. weiter lesen »

Agile: Definition of Done und Failure Mode Programming

Einer der Begriffe, die bei Agilen Softwareentwicklungsprozessen immer wieder zu hören sind, ist “Definition of Done” (DoD). Man soll also vorher definieren, was man unter “fertig” versteht. Das hört sich erstmal trivial an. Und der triviale Grund, dass man ansonsten aneinander vorbei redet, leuchtet auch jedem ein.

“Ist Feature X jetzt endlich fertig?”
“Ja, hab ich gestern eingecheckt.”
“Dann können wir morgen also deployen.”
“Neinnein, da muss noch die QA drüber. Da ist noch nix getestet.”

“Ist Feature Y jetzt endlich fertig?”
“Fast. Zu 90% ist es fertig. Ich muss nur noch…”

Wenn man einmal definiert, was “fertig” bedeutet, kommt es zu weniger Missverständnissen. Mal ganz davon abgesehen, dass man so auch leichter dieses “fast fertig” ausmerzen kann. Entweder ist ein Feature “done” oder eben nicht. Zu 90% fertig bedeutet ja meist, dass noch (weitere) 90% vor einem liegen. Das ist die so genannte 90-90 rule. Und diese ist nur zu oft wahr. Auch, wenn mans vielleicht nicht wahr haben will (mich teilweise auch noch eingeschlossen; ich arbeite daran).

Das ist alles klar und allgemein bekannt. Aber es gibt noch einen anderen Grund für eine DoD: weiter lesen »

Agile: Frequency Reduces Pain

Quasi alle mir bekannten agilen Methoden basieren auf einem weiteren grundlegenden Gedanken, der allerdings nur selten genannt wird, wenn Agile Softwareentwicklung erklärt wird: Frequency Reduces Pain oder anders ausgedrückt: “if it hurts, do it more often”. Integration, Tests, Schätzungen, Refactoring, alles das kann sehr unangenehm werden. Deshalb wird das alles in agilen Prozessen viel öfter gemacht — in kleineren, überschaubareren Schritten.

Integration kann man nicht vermeiden. Irgendwann muss man eben mal alles zusammenwerfen und gucken, ob es funktioniert. Je größer die Software und je später die Integration, desto schwieriger wird das Ganze. Deshalb macht man es viel öfter. Nämlich mindestens einmal täglich. Und auf einmal wird alles viel einfacher.

Schön zusammengefasst ist das außerdem in Gall’s Law:

A complex system that works is invariably found to have evolved from a simple system that worked. The inverse proposition also appears to be true: A complex system designed from scratch never works and cannot be made to work. You have to start over, beginning with a working simple system.

Integration ist nur ein Beispiel. Das genannte Prinzip steckt in ganz vielen agilen Praktiken und ist außerdem der Grund dafür, dass agile Prozesse hochgradig iterativ sind: Wenn es schwer ist, Software fertig zu kriegen, dann kriegen wir sie eben alle zwei Wochen fertig. Wenn Schätzen schwer ist, dann schätzen wir eben alle zwei Wochen neu, aber dafür kleinere Arbeitspakete. Wenn Testen nervig ist, machen wir es zum Prinzip und schreiben Tests vor dem eigentlichen Code, sodass unser Code unweigerlich testbar wird. Wenn Refactoring fehleranfällig ist, machen wirs doch besser andauernd — immer mal wieder ein bisschen.

Softwareentwicklung ist wie Markklößchensuppe essen: Nicht alle auf einmal, sondern einer nach dem anderen.

Agile: Was ist das eigentlich?

In der letzten Zeit hab ich mich eingehend mit agiler Software-Entwicklung beschäftigt. Das hatte ich schon eine ganze Zeit lang vor, aber praktischerweise hatte ich von der Uni aus die Aufgabe mit ein paar Kommilitonen mir Scrum anzusehen und darüber zu referieren. Außerdem habe ich gerade an der Summerschool “Agile Software-Entwicklung” teilgenommen. Das hab ich dann mal zum Anlass genommen, mich etwas intensiver mit der Thematik zu beschäftigen.

Bei Agiler Softwareentwicklung gehen die Meinungen typischerweise stark auseinander. Je nachdem wem man zuhört, ist man geneigt entweder den einen oder den anderen recht zu geben. Beide Argumentationsweisen, beide Softwareentwicklungsphilosophien hören sich, für sich alleine betrachtet, vollkommen vernünftig an. Das hilft natürlich nicht sonderlich weiter, wenn man sich eine eigene Meinung bilden will und so schreibe ich das hier hauptsächlich, um mir selbst hier einigermaßen Klarheit zu verschaffen.

Ursprünglich hatte ich einen vergleichsweise langen Artikel geplant. Ich denke aber, dass mehrere kleinere Artikel eher gelesen werden als ein großer. Außerdem dauert ein großer Artikel immer so lange zu schreiben. Nachdem ich jetzt schon über zwei Monate immer mal wieder an dem Text sitze und immer noch erst etwa ein Drittel steht, habe ich mich nun entschlossen, eine Artikelserie daraus zu machen.

Die Artikelserie spiegelt meine momentanen Gedanken zu dem Thema wider. Ich kann nicht sagen, ob ich bei dieser Meinung, die ich hier mal herausarbeite, bleiben werde. Ich bin einfach selbst mal gespannt, wie ich zur Thematik stehen werde, wenn ich mit der Zeit mehr Einsicht gewinne. Nun gut. Ich hab jedenfalls einiges gelesen und mir meine Gedanken dazu gemacht. Los geht es mit einem geschichtlichen Überblick über die Thematik.
weiter lesen »

Summerschool “Agile Software Development”

Der FIT hat in diesem Jahr neben den schon mehrmals angebotenen — und im übrigen ebenfalls empfehlenswerten — Firmenexkursionen auch eine Veranstaltung zum Thema Agile Softwareentwicklung angeboten: Summerschool “Agile Software Development”.

Als ich die Ankündigung gelesen hatte, wusste ich sofort, dass ich da mitmachen wollte. Mit agiler Softwareentwicklung wollte ich mich sowieso mal beschäftigen. Außerdem sollte das Ganze auch sehr praxisnah sein. (Wenn man auf ner Uni studiert, sind wirklich praxisnahe Lehrveranstaltungen eher selten.) Und zum Dritten bot sich so mal wieder die Gelegenheit, mit ein paar Firmen in Kontakt zu kommen. weiter lesen »

Wollt ich nur mal gesagt haben…

  • Redundanzen sind doof.
  • Variablen, die eigentlich lokal deklariert sein könnten, aber als Attribut in der Klasse stehen, sind eklig.
  • Variablen, die als String deklariert werden, obwohl sie Integers, enums oder gar Objekte sein könnten, sind scheußlich.
  • Objekte, die erzeugt, aber nicht verwendet werden, sind sinnfrei.
  • Magic Values sind böse.
  • Konstanten sind nicht böse. Man darf sie ruhig verwenden.
  • Bezeichner, die nicht das kommunizieren, was sie bezeichnen, sind nervig.
  • Bezeichner, die absolut gar nichts aussagen, sind <hier stark negativ besetztes Adjektiv einsetzen>
  • Lange Parameterlisten sind schwer lesbar und zeugen von schlechtem Design.
  • Wenn ich bei Methoden Parameter abzählen muss, um zu gucken, ob ich einen vertauscht hab, ist da etwas faul.
  • Wenn ich Parameter mit Dummy-Werten füllen muss, läuft da was schief.
  • Magic Values sind böse.
  • Objektorientiert programmiert man nicht, wenn man irgendwie Objekte verwendet, sondern, indem man objektorientiert denkt.
  • Objekte sind etwas anderes als Tabellen. Ja, wirklich.
  • if (a == null) return null; else return a; ist das selbe wie return a;
  • REST ist jetzt nicht furchtbar kompliziert. Aber den Unterschied zwischen Ressourcen und Verben sollte man schon verstanden haben.
  • Passwörter speichert man nicht im Klartext.
  • SQL Injection kann man verhindern
  • Magic Values sind böse.
  • Eine Klasse mit über 800 LOC ist vermutlich eher weniger “simple”.
  • NullPointerExceptions sollte man nicht fangen, sondern verhindern.
  • Obsoleten Code kann man entfernen. Man benutzt dazu wahlweise [DEL] oder [Backspace].
  • Code einheitlich einzurücken, tut nicht weh. Zumal einem die IDE dabei helfen kann.
  • Fehlerbehandlung heißt nicht, im Fehlerfall nen Stacktrace auszugeben und dann einfach weiter zu machen, als wär nichts gewesen.
  • Hab ich schon erwähnt, dass Magic Values böse sind?
  • Meine Zehnägel tun weh.

Wollt ich nur mal loswerden…

SoftwareArchitekTOUR: Patterns in der Java-Welt

Gerade gehört: SoftwareArchitekTOUR: Patterns in der Java-Welt. Vor einiger Zeit hab ich die ersten beiden Episoden gehört. Jetzt hab ich mir mal diese angetan.

Und natürlich kann ich mich gewisser Kommentare nicht enthalten:

  • Double-Checked-Locking wird erklärt. Allerdings wird nicht darauf verwiesen, dass das Pattern kaputt ist. Zumindest wenn man kein volatile benutzt. Nähere Infos in der Wikipedia
  • Es wird davon gesprochen, dass das get/set-Idiom dazu verleitet, es überzuverwenden. Also man macht überall Getter und Setter und vergisst dabei, der Klasse sinnvolle Methoden zu verpassen. Die Problematik sehe ich auch. Ich frage mich nur momentan, ob Properties wie in Delphi/C#/Ruby/etc. hier einen Einfluss haben und wenn ja welchen. Positiv oder Negativ? Ich vermute einen positiven Einfluss, bin mir da aber nicht ganz sicher.
  • Immutability wird IMHO leider schlecht erklärt. Es geht natürlich nicht nur darum, dass Objekte mit gleichem Wert gleich sind, sondern auch, dass die Objekte (mehr oder weniger) zustandslos realisiert werden.
  • DependencyInjection hätte ich wahrscheinlich nicht verstanden, wenn ich nicht schon wüsste, was es ist. Generell scheint es mir so zu sein, dass der Podcast nur einen groben Überblick und ein paar Buzzwords liefert. Das hört sich jetzt wie vernichtende Kritik an, aber so ist es nicht gemeint. Überblick geben ist gut. Viel mehr kann man in ner dreiviertel Stunde auch nur schwer abhandeln. Man darf nur nicht mit falschen Erwartungen an den Podcast rangehen.
  • Zu Multiple Dispatch hab ich schonmal was geschrieben.

Enbugging — Wie wir Fehler machen und wie wir sie vermeiden

Wie im letzten Jahr, hab ich auch dieses Mal wieder einen Vortrag auf den Delphi-Tagen gehalten. Diesmal gings ums Fehler vermeiden. Man könnte auch sagen, um konstruktive QA-Maßnahmen. Egal. Jedenfalls gings um Bugs.

Abstract

“Wenn Debugging der Vorgang ist, Fehler aus einem Programm zu entfernen, dann ist Programmierung der Vorgang, Fehler in ein Programm einzubauen.” So liest man zuweilen im Netz und manchmal ist es nur zu wahr. Stunden verbringen wir damit, umständlich einen Fehler zu suchen, den wir zuvor noch ganz mühelos einbauen konnten. Wäre es da nicht praktischer, statt uns mit Debugging aufzuhalten, das Enbugging, das Einfügen von Fehlern gar nicht erst zu betreiben? Letztendlich sind wir ja eigentlich selbst schuld: Bugs entstehen nicht aus dem Nichts. Vielmehr erzeugen wir — meist unabsichtlich — Bedingungen, unter denen diese kleinen Krabbelviecher so prächtig gedeihen. Dieser Vortrag soll zeigen, wie Bugs entstehen und was wir dagegen tun können. Eine vollständige Betrachtung des Themas kann dabei natürlich nicht erfolgen. Stattdessen wird ein Überblick gegeben, um danach einzelne Aspekte zu vertiefen.

Folien

Wie versprochen gibts hier die Vortragsfolien: Download: Enbugging (Größe: 1.14 MB; bisher 157 mal heruntergeladen)

Ich hab wieder eine Gratwanderung zwischen vortragsunterstützenden Folien und Infos für alle, die den Vortrag nicht gesehen haben, versucht. Ob mir das gelungen ist, darf jeder selbst beurteilen (und mir am besten auch noch ein bisschen Feedback geben).

Hinweise

  • Eigentlich wollte ich noch erwähnen, dass Tony Hoare (der übrigens auch den QuickSort erfunden hat) auch dran schuld ist, dass in Pascal die geschweiften Klammern Kommentare sind. Hoare hat Vorbedingungen und Nachbedingungen in geschweiften Klammern vor bzw. hinter Code geschrieben (“Hoare-Tripel“) und damit formale Verifikation gemacht. Niklaus Wirth gefiel das Ganze so gut, dass er die geschweiften Klammern zu Kommentarzeichen machte.
  • Um die Beispiele zu verstehen, sollte man sich genau angucken, wie die Bezeichner (insbesondere die Klassen) heißen. Man sollte daraus erraten können, worum es geht. Meine Beispiele waren meist allgemein bekannte Datenstrukturen (List, Map, Set) oder standen in losem Zusammenhang mit Feedreadern, HTML-Parsern u.ä.
  • “Meine Fehlerliste” enthält viel zu wenige Daten, um hieraus schon etwas Sinnvolles ableiten zu können. Da muss ich noch mehr sammeln. Das hab ich beim Vortrag zwar schon dazu gesagt, aber es steht so explizit nicht in den Folien.
  • Was ich auch im Vortrag erwähnt hab, aber nicht auf den Folien steht: Bidirektionale Assoziationen sind starke Kopplungen. Also wenn sich zwei Module gegenseitig kennen, anstatt dass nur ein Modul das andere kennt, aber nicht umgekehrt. Man sollte deshalb zusehen, dass man möglichst nur einseitige Beziehungen hat.
  • Der Anhang enthält noch weitere Beispiele und Hinweise auf weiterführende Themen, die nicht angesprochen werden konnten.

Errata

  • Auf Folie 60 fehlt ein not. Es müsste also heißen if not FInnerList.Contains(item) then.

Bitte um Feedback

Das Feedback, das ich bisher bekommen hab, war durchweg positiv. Das freut mich. Ich will hier aber trotzdem nochmal nach Feedback und explizit auch Kritik fragen. Nur, wenn ich weiß, was ich besser machen kann, kann ich in Zukunft etwas weniger schlimme Vorträge machen… *g*

Insbesondere würde mich folgendes interessieren:

  • Hab ich verständlich geredet? War ich vielleicht zu schnell?
  • Waren die Beispiele verständlich? Nachvollziehbar? Praxistauglich?
  • Wie versteht man die Folien, wenn man sich den Vortrag nicht angehört hat?
  • Waren Thema und Inhalt angemessen? Zu theoretisch? Zu einfach? Zu schwer? Zu trivial?
  • Kann ich sonst etwas verbessern?

powered by WordPress | QuickLaTeX | WordPress Themes