Wir wissen jetzt, dass Refactorings dazu dienen,
die Wartbarkeit, die Veränderbarkeit von Code zu verbessern,
damit eine längere Lebensdauer zu erreichen,
damit das am Ende die Struktur zu verbessern.
Und damit denken wir, wissen wir schon gut gerüstet und wir wissen,
da gibt es welche im Katalog, wir werden da schon was finden.
Aber sie werden ganz schnell feststellen, wenn sie das praktisch
machen wollen, dass es da viel zu viel gibt.
Wir müssen uns konzentrieren, wir müssen uns fokussieren,
wir müssen Prioritäten setzen, wie es immer so schön heißt.
Und dazu dient das Schema, um das zu verdeutlichen,
dient das Schema,
was wir hier auf diesem Bild sehen
Und zwar starten wir mit Refactorings, mit den Zielen,
die eines Projektes. Natürlich, das sagte die Definition,
vor allen Dingen geht es um Wartbarkeit. Ja,
aber Wiederverwendbarkeit hat auch etwas damit zu tun und Testbarkeit ist auch ein Aufwand,
der Testaufwand ist auch etwas, was bei Änderungsaufwand mit reinfließt.
Ja, und ganz häufig ist Effizienz auch ein Veränderungsziel,
auch wenn es nicht bei Refactoring so ganz klar genannt war.
Wenn wir diese mehreren Ziele haben, so widersprechen Sie sich teilweise.
Auf jeden Fall widersprechen Sie sich mit dem Verfügbaren
und Sie führen den Konflikt mit dem verfügbaren Arbeitsaufwand,
den wir investieren können
Können, häufig sind es viel zu wenig Leute für viel zu große Systeme,
die so ein Reflektoring machen können,
die Wartungen machen können, hat einfach damit zu tun,
in so einem Wartungsvertrag wird nicht so viel Geld investiert.
Da sind also nur wenige Leute davon zu bezahlen und die müssen ein relativ großes System betreuen.
Diese paar wenigen Leute müssen sich also konzentrieren.
Wie legen wir das? Wie machen wir das? Wenn wir natürlich sagen,
so wir haben eben ja gesagt, okay,
wir machen erst die Veränderungen Richtung Verbesserung,
also erst das Reflectoring und dann machen wir die Veränderung,
die der Kunde wirklich will für das Stückchen,
dann können wir ja schon sagen, ja, so
Da sind wir lokal beschränkt. Aber welche Art für eine
Veränderung wir machen? Worauf will legen wir besonders wert?
Das hat was mit Prioritäten zu tun.
Und hier können wir durchaus von den Projektzielen ausgehen.
Solche Projektziele können eben wiederverwendbar sein, keine Entwartbarkeit oder Testbarkeit
oder so etwas sein. Und wir können das so machen,
dass wir dieses erstmal dieses relativ globale Ziel zerlegen in kleinere Ziele.
Zum Beispiel, wir wollen sagen, wir machen viele Fehler
dadurch, dass wir es missverstehen.
Also Lesbarkeit, das Kurz ist wichtig. Einfachheit ist Kurz,
ist wichtig. Oder viele Sachen sind bei uns so,
dass wir Probleme haben, Die Änderungen lokal zu begrenzen, in unserem Projekt.
Änderungen breiten sich weit aus, weil wir zu viel Abhängigkeit haben.
Lasst uns Modularisierung als wichtiges Kriterium nehmen. Wir Modularisierung als
das wichtige Ziel beim Reflektor hin. Oder wieder vielleicht in einem anderen Projekt,
sind viele Entwickler, die eigentlich vorher mit anderen Programmiersprachen gearbeitet haben,
die vorher C Plus C Sharp oder was anderes gemacht haben und die jetzt zu Java kommen.
Und die kennen die Sprache nicht so richtig. Lasst uns vor allen Dingen gucken,
dass das eine gute Verwendung der Sprache ist,
dass man gut verständliche Sachen macht,
dass da nicht irgendwelche Tricks drin sind,
so quasi unter der Überschrift,
ja,
funktioniert sogar
Ganz schlecht, ganz schlecht, weil von anderen nicht verständlich,
nicht wartbar. Man baut dann eher einen Ärger drumherum,
damit es wieder, wenn man es ändern muss.
Also Sprachstandards einhalten. Oder wir haben bestimmte Projektregeln,
die Einheitlichkeit, das geht von VfB Namensungen los,
was ist Deutsche, was ist Englisch, bis hin zur Struktur,
zur fachlichen Gliederung, dass man, oder welche Technologien,
welche Frameworks wir benutzen und welche eher nicht,
dass man solche Umstrukturierungen auch macht.
Je nachdem, was das Ziel ist und daraufhin wählt man dann aus,
welche Bad Smells und wir kommen jetzt gleich dazu,
was das eigentlich ist. Welche nehmen wir als Indikator,
was zu tun oder welche Richtlinien wenden wir an, um Änderungen vorzunehmen.
Also dieses Priorisieren machen wir mit einem Top-Down-Ansatz, also top,
ist sozusagen die Qualitätsziele auf der obersten Ebene,
dann zur verfeinern wir das, was sind Entwurfsziel,
Entwurfsprinzipien und dann wählen wir aus, was sind die Anzeiger,
nach denen wir uns richten wollen, um zu entscheiden,
welche Kriterien, welche Reflectorings wir hier wirklich machen.
Soweit nur noch einen Blick zurück zu den Fragen, was wir jetzt weitermachen.
Wir hatten jetzt schon die ganze Zeit über Bad Smells gesprochen,
das wären wir jetzt mal tun und auf den folgenden Folien haben sie Klassentypen von Bad Smells stehen,
mit einigen Vertretern, jeweils die namentlich genannt sind.
Wir gehen hier nicht auf die, das lässt die Veranstaltung leider nicht zu,
dass wir hier ganz detailliert auf die einzelnen Bad Smells eingehen.
Ich sage kurz was dazu, damit sie wissen,
warum in diese Kategorie sowas fällt und ich möchte sie einfach ermutigen,
sich das nach und nach im Arbeiten mit existierenden Systemen zu erschließen,
indem sie dann merken, oh,
das und das,
das habe ich doch dort untergeben in dem Namen als
Bad Smell gehört
Die Bets Milz, die erste Gruppe,
sind die Sachen, die zu groß sind.
Ich habe hier eine ganz interessante Masterarbeit gefunden,
die habe ich in der Literaturquelle eingegeben,
für die von Ihnen, die aufmerksam sind.
Sie haben diese Literaturquelle auch in SE2 schon gehört.
Vielleicht hat sogar der ein oder andere mal reingeschaut.
Also der Link funktioniert noch, das heißt, Sie finden
das dort. Und die erste Klasse sind die Sachen,
die zu groß sind.
Ja,
zu groß hat mehrere Auswirkungen
Auswirkungen, vor allen Dingen auf Wartbarkeit. Man kann
die Sachen schlecht lesen. Die Sachen sind häufig unstrukturiert,
schlecht, wenig übersichtlich. Das sind Sachen,
die uns am Ende hindern, Veränderungen gut zu machen.
Das Risiko ist nicht nur, dass man die Übersicht verliert,
Beeinträchtigungen,
Durch fehlende Übersicht. Also zum Beispiel im Fall von Long Method oder Large Class,
wenn wir etwas haben, was deutlich über ein,
zwei Seiten hinausgeht als Methode,
dann fällt es uns schwer zu überblicken,
was macht die lokale Variable hier oder was ist dort überhaupt im Ablauf drin.
Also das wird immer schwieriger oder wenn wir sehr viele Parameter haben,
dann ist das Risiko, dass wir den Überblick verlieren,
relativ groß.
Also die fehlende Übersicht ist das eine
Aber sehr wahrscheinlich ist es auch noch so,
dass Dinge vermischt sind. Also wahrscheinlich schreibt sich mit Haar
. Sehr wahrscheinlich schlechte Trennung von Zuständigkeiten
Deswegen sollten wir hier eine Zerlegung machen, das ist ganz klar,
irgendwie klein machen. Ist das Gegenmittel gegen dieses Bad Smell
? Die nächste Kategorie von Bad Smells sind welche,
die bei den Objektorientierungen nicht richtig verstanden oder nicht richtig angewendet worden ist.
Das Problem ist dann häufig, dass es auch dabei kommt,
dazu kommt, dass Earl, wir wollen das hier nicht malen,
sondern wir wollen hier nur zeigen,
dass die Wartbarkeit beeinträchtigt wird, insbesondere Verständlichkeit,
aber auch die Erweiterbarkeit beeinträchtigt wird,
weil wir viel zu viel Abhängigkeiten reinbekommen
Solche Sachen zum Beispiel entstehen, indem man temporäre Variablen nutzt,
wo eigentlich Feldern mit lokaler Sichtbarkeit,
also mit Private-Attributen sein sollten oder lange Reihen von Entscheidungen über Switch-Statements
statt über Schalter und Zustände, Stuhlstände abgebildet werden können.
Oder dass man die Unterklassen nicht wirklich Vererbung nutzen,
sondern da ist mir gar nicht klar, warum sind das Unterklassen?
Oder dass es Klassen gibt, die unterschiedliche Interfaces haben,
die aber nicht zusammenpassen,
die nicht wirklich eine eine Unterklasse sind im Sinne von Spezialisierung.
Ich gehe hier nicht weiter im Detail darauf ein,
weil bitte lesen Sie es gerne mal nach.
Wir werden das, ich möchte hier darauf aufmerksam gemacht haben,
wie Objektorientierung missbraucht werden kann, erstmal nur vom Titel her.
Die nächste Kategorie, die wir haben, sind welche,
die uns beim Ändern hindern.
Im Sinne von Change Preventor im Sinne von zu hohem Aufwand.
Solche Dinge mit hohem Aufwand sind zum Beispiel,
dass wir Vererbungshierarchien in Parallelenformen ausgebreitet haben, dass wir etwas haben,
wo die Veränderungen sich überall hin ausbreiten.
Ja, also wenn ich etwas ändere, muss ich überall eingreifen.
Das ist so eine Änderung oder eine andere mit dem lustigen Namen Shotgun,
Searchery, also Volutze Verletzung durch Schrotschuss sozusagen.
Ich muss viele Klassen beeinflussen, anfassen, wenn ich eine kleine Änderung mache.
Das sind Dinge, wo Abhängigkeiten entstehen,
die eigentlich nicht sein müssen, Komplexität, die eigentlich nicht sein muss.
Und indem wir das beheben, können wir sehr dazu beitragen,
dass Fehler vermieden werden, dass Änderungen weiter möglich sind,
dass die Wartbarkeit im Sinne von Aufwand auf einen Veränderungen verringert wird.
Also hier Erwartbarkeit als ganz wesentliches Ziel. Ich meine,
es überrascht nicht. Wir hatten ja schon ganz Anfang gehört,
Refactoring zielt Aufwandbarkeit. So, die Dinge, die irgendwie,
die man irgendwie loswerden kann, die man wegschmeißen kann.
Da gibt es zum Beispiel Lacy Clar, ist eine Klasse,
die eigentlich scheinbar fast nichts tut oder eine Datenklasse, die kein Verhalten hat.
Code Clones, Duplicate Code oder toter Code oder auch Sachen,
das ist auch ganz besonders beliebt,
wo mir jemand etwas super Allgemeines bauen will,
die universelle Maßeinheiten,
Umrechnungsklasse,
die man nie braucht
Ja, also man sollte ja immer, sie lernen das mit Objektorientierung,
mit Scrum, mit agilen, iterativen Vorgehensweisen.
Man sollte das alles so einfach wie möglich machen.
Und das, dass man hier spekuliert, dass man später
das mal brauchen würde, das kann man alles vereinfachen.
Und diese Einfachheit, die trägt eben dazu bei,
dass ich weniger zum Pflegen habe, dass die Änderungen leichter fallen.
Verständlichkeit sowieso, aber eben auch Erweiterbarkeit und Testbarkeit.
Dann gibt es welche, die ganz speziell ihre Schwächen,
oder wo wir die Schwächen damit umreißen,
die um Kopplungen geht
Ungeeignetes, unangemessene, enge Kopplung, meistens eben enge Kopplung,
Neid, Feature Nvy, also eine Klasse ist eine Methode,
ist ganz stark mit Feldern von anderen Klassen oder mit Methoden von anderen Klassen,
von beiden verbunden und gar nicht so sehr mit Sachen der eigenen Klasse.
Also ich möchte gern überall verantwortlich sein, dann sollte man
diese Methode dorthin verlagern, muss ich gern was zu tun haben will.
Oder dass die Intimität verletzt wird im Sinne von,
ich gebe interner Preis, die ich eigentlich lokal halten sollte.
Wenn ich das tue,
wenn nicht zu viel von den Internen nach außen gebe,
dann sind Änderungen dieser interner Führung immer auch dazu,
dass sich das alles, was außen davon gebraucht macht,
sich darauf verlässt, was sich dann ändern muss.
Etwas, dieses Message Chain hier, das haben Sie hoffentlich noch gut in Erinnerung.
Ja, das war das Lore of Demeter,
also enge Kopplung, zum Beispiel durch solche Referenzketten.
Das sollte man auf jeden Fall vermeiden. Oder Middleman,
dass man da eine Kopplung hat, indem man,
oder die Kupplung verringert, indem man da noch was dazwischen schaltet.
Also hier auch vor allen Dingen die Erweiterbarkeit ist etwas,
was ganz stark davon profitiert, wenn wir kopplunglose gestalten.
Die Testbarkeit, wenn wir Dinge entkoppeln und die Einfachheit,
Unverständlichkeit, indem wir Dinge nach Zuständigkeiten trennen. Genau,
bevor wir hier weitergehen mit dem Refactoring,
möchte ich doch kurz etwas dazu sagen,
warum wir Bad Smells für so wichtig halten,
warum Bad Smells die Entscheidungskriterien sind für die Refactorings
Bets Merz. Als Entscheidungskriterium und Indikatoren. Wenn wir
über Refactorings zu entscheiden haben, entscheiden wir über Arbeitsaufwand.
Und da gibt es ganz unterschiedliche Kriterien.
Warum sollte man jetzt
ein Refactoring machen
Entscheidungen über Refactorings. Könnte man jetzt machen,
dass man sagt, das sieht irgendwie komisch aus.
Ja, das ist irgendwie, das heißt, wir sind bei Ästhetik.
Sie kennen vielleicht diesen Spruch, Ästhetik liegt im Auge des Betrachters.
Man kann über Ästhetik, über Schönheit nicht diskutieren.
Das empfindet jeder anders. Ästhetik schreibt sich mit einem Haar,
das machen wir hier auch,
so viel Zeit muss sein
Ästhetik, ja, da kann sie sie sagen,
das finde ich komisch und da sagt der Kollege zu ihnen,
ach, ich finde es ganz gut.
Und was können sie da machen? Nichts mehr. Also Ende
der Diskussion, damit können sie schlecht Refactoring-Bedarf begründen. So,
das war das Zweite ist, wo jemand auf die Idee kommen wird,
das könnte man nehmen als Anzeiger, da ist etwas Schlechtes,
könnte man sagen, Metriken.
Ja, es gibt Metriken, die sagen, wenn etwas zu groß wird.
Die Metriken, die sagen, wenn irgendwo Bedingungen zu komplex sind.
Wenn die Vererbungstiefe zu tief ist, all dafür gibt es
Metriken, ja, wunderbar können wir verwenden.
Tatsächlich verwenden wir die auch teilweise. Aber das Problem ist,
sie flächendeckend einzusetzen, liefert auch nur flächendeckende Restaurant, also flächenbezogene Resultate.
Es hilft wenig bei der Entscheidung im Einzelfall.
Ich will nicht sagen, sie helfen nicht, aber helfen,
wenig bei Entscheidungen im Einzelfall. Wir müssen rauchen,
haben die immer im Vergleich zu anderen immer im Vergleich
oder für größere Einheiten
So, dann können wir natürlich noch sagen, okay,
ich habe hier so ein Bauchgefühl. Das ist,
ich kriege hier ein schlechtes Gefühl, wenn ich das lese.
Das wäre Intuition. Ja, Intuition, Intuition,
ja, so richtig geschrieben, hoffe Morill.
Intuition ist tatsächlich ein wichtiges Kriterium für viele Entscheidungen,
ja, wenn Sie überlegen,
will ich mein Haus dort hinbauen an diesem Südhang oder an den Nordhagen,
dann ist es ganz gut,
da mal hinzufahren und sich mal ein Gefühl dafür zu holen,
weil es eine komplexe Entscheidung ist
Haben wir auch komplexe Entscheidungen. Aber wir würden gern diese Entscheidung begründen.
Wir entscheiden ja schließlich über Aufwand, denen irgendjemand bezahlen muss.
Und das ist bei Intuition relativ schlecht möglich. Wenig nachvollziehbar,
schreibe ich mal dazu. Aber wir können natürlich den Oberexperten
nehmen und der sagt uns das, das ist schlecht,
da wird keiner widersprechen und dann ist das die Entscheidung.
Nur viele Projekte haben nicht so einen Oberexperten,
den sie immer mal gleich rufen können jede zweite Woche
Das heißt, wir müssen irgendwie selbst das entscheiden, ja.
Und ich schreibe mal noch dazu, es sind ja schließlich Investitionsentscheidungen.
Es sind ja schließlich. So, jetzt,
der Vorschlag für Sie völlig überraschend, Bads,
Merz sind das gute Kriterium
Ben Smell als gutes Entscheidungskriterium. Erfahrung ist dort eingeflossen.
Das ist ein wichtiger Punkt. Die Ben Smells sind entstanden aus
der Erfahrung von vielen. Und sie sind vielmals diskutiert worden.
Und sie ist ein unzweifelhaft, dass das etwas Schlechtes ist.
Also wenn sie da irgendwas finden und das ist so und so,
kommt ihnen komisch vor und sie finden im Bad Smell,
was sagt, was deinen Namen dafür gibt und sagt,
hier hast du dieses Bettsmerl verwendet, das ist schlecht,
dann kann man ganz schlecht diskutieren.
Ja, und dann kann man das nicht gut wegdiskutieren,
von wegen, it's not a bug, it's a feature.
Oder irgendwie, ich habe aber ein gutes Gefühl dabei oder so.
Nein, es ist ein Bettsmerl. Das Zweite,
was wir weswegen wir sagen können, sind Betsmerls sind gut,
weil Betsmerls häufig auch ein Verweis auf die Lösung enthalten.
Enthalten Hinweise auf Lösung, beziehungsweise Reparatur. Durch Refactorings. Ja,
ein bisschen wieder am Dozenten versteckt, aber das kann man sich schon mitgekriegt.
Also durch Refactorings. So, das ist also,
deswegen sind Bad Smells sehr gut als Entscheidungskriterium, geeignet.
Das sagte uns auch diese Frage, will das von uns wissen?
Wir gehen mal hier zurück zu der Frage, welche Rolle
spielen Bad Smells beim Refactoring? Ja, ganz überraschend,
die Bad Smells sind das Entscheidungskriterium, welches Refactoring wir nehmen können.
So, bevor wir in ein Beispiel gehen,
erstmal kurz noch den allgemeinen Ablauf, ach so,
ich springe mal hier eins vorher,
hier zeige ich mal einen Refactoring-Katalog, wo alles Mögliche drinsteht.
Ja, also Introduced Duplication, Duplicate Feature,
elimitated Duplication by Composition oder einfach nur solche Sachen wie
Extract Method oder so stehen hier nicht drin.
Das ist einfach eine Ergänzung. Leider gibt es die nicht
mehr in ganz genau dieser Form. Sie finden sie eben
mittlerweile ein bisschen ähnlich. Deswegen habe ich die jetzt hier
auf die Webseite, auf die Folie kopiert.
Man kann die einzelnen dann schon noch finden. Ich möchte
noch etwas zum prinzipiellen Aufbau sagen. Ich hatte erläutert bei dem Kapitel,
bei dem Abschnitt Risiko, dass man immer in kleinen Aufgaben,
in kleinen Schritten vorgeht, um dann etwas um dann noch eine größere Lösung,
größere Änderung zu erreichen.
Aber jeder kleine Schritt kann rückgängig gemacht werden.
Und diese kleinen Schritte führen erst mal manchmal dazu,
dass ich erst mal hier etwas durchaus erst mal etwas vergrößere,
bevor ich es verkleinere.
Ja, also hier ist das Zusammenfassen von etwas Gemeinsamen gezeigt.
Ja, ich bilde erst mal eine Oberklasse.
Da wird erst mal etwas mehr. Und dann verlagre ich
das Gemeinsame von der Unterklasse in die Oberklasse.
Und dann wird es erst weniger und dann bleibt hier unten
nur noch das übrig, was ich brauche.
Also erst würde das mal kopiert und dann würde das eingefügt
Diese kleinen Schritte, jeder dieser kleinen Schritte,
ich gehe noch mal zurück zu der Folie,
die das sagte, mit den Kriterien.
Also wir haben hier diese Folge kleiner Schritte. Jeder kann
einfach geprüft werden. Also nach jedem Schritt machen wir einen
Test. Und er kann bei Bedarf rückgängig gemacht werden.
Und jetzt kommen wir im nächsten Abschnitt dazu,
dass wir so ein kurzes Beispiel erklären, dazu.
Aber dazu stoppen wir hier und machen einen neuen Abschnitt