Wprowadzenie do zasad SOLID - czyli jak pisać SOLIDny kod MICHAŁ BRZOZOWSKI Architekt i Kierownik Zespołu
Jak poznad zły kod?
Znamiona złej architektury Sztywnośd (Rigidity) Tendencja do tego że system jest trudno zmienid. Nawet w najprostszy sposób. Każda zmiana powoduje kaskadowe zmiany w modułach zależnych Miła dwu dniowa robótka zmienia się w niekooczący się maraton Kierownicy nie pozwalają naprawiad nie krytycznych błędów Koszty są nie przewidywalne
Znamiona złej architektury Delikatnośd (Fragility) System zaczyna się psud w wielu różnych miejscach przy każdej zmianie Błędy pojawiają się w module który nie ma logicznego powiązania z modułem zmienianym Przy naprawie system psuje się w nieprzewidywalny sposób Każda poprawka pogarsza sytuację wprowadzając więcej problemów niż rozwiązując
Znamiona złej architektury Bezruch (Immobility) Brak możliwości re-użycia części systemu Użyteczne moduły maja zbyt wiele zależności Koszt przepisania od nowa jest mniejszy niż ryzyko związane z odseparowanie zależności Moduł ma zbyt wiele bagażu
Znamiona złej architektury Lepkośd (Viscosity) (projektu i środowiska) Zmiany w systemie zawsze można zrobid na kilka sposobów. Niektóre takie zmiany współgrają z bieżącą architektura/projektem inne nie (np. różnego rodzaju obejścia i haki). Jeśli zmiany współgrające z architektura są trudniejsze do wprowadzenia niż obejścia mówimy o dużej Lepkości systemu. Przemyślane zmiany w projekcie są trudne do wykonania Łatwiej wykonad coś złego niż dobrego
Dlaczego? Dlaczego system staje się? Sztywny Delikatny Nieruchawy Lepki Zbyt mocne/niepotrzebne zależności pomiędzy modułami!
Co zrobid? Zapewnid Dużą kohezję (High Cohesion)!!!
Kohezja (Zwartośd, spoistośd): Miara określająca jak silno powiązane i podobne są poszczególne odpowiedzialności modułu/klasy Wikipedia wolne tłumaczenie Object Oriented Principles
Co zrobid? Zapewnid Dużą kohezję (High Cohesion)!!! Luźne powiązania (Low Coupling)!!!
Coupling (powiązanie, połączenie, szczepienie): Miara określająca stopieo w jakim moduły/klasy zależą od siebie. Wikipedia wolne tłumaczenie Object Oriented Principles
Co zrobid? Zapewnid Dużą kohezję (High Cohesion)!!! Luźne powiązania (Low Coupling)!!!
Craftsmanship over over Execution Crap SOLDI -> SOLID
SOLID Software Development to nie gra Jenga
OLID
ingle responsiblity princile Zasada pojedynczej odpowiedzialności Klasa powinna mied jedną odpowiedzialnośd
Klasa Employee public class Employee { public string Name /*...*/ /* wszystkie inne wlasciwosci */ public PayInfo CalculatePay() public EmplyeeReport GenerateReport() public void SaveToDb() //kolejne 100 metod } EmployeePayCalculator EmployeeReportGenerator EmployeDBsaver 1 100
S LID
pen/closed Principle Zasada otwarte-zamknięte Operacja na otwartym sercu nie jest potrzebna przy ubieraniu płaszcza
public void DrawAllShapes(Ilist<object> shapes) { foreach(var shape in shapes) { if(shape is Circle) DrawCircle((Circle)shape); else if (shape is Square) DrawSquare((Square)shape); } } public void DrawAllShapes(Ilist<Shape> shapes) { foreach(var shape in shapes) { shape.draw(); } }
SO ID
iskov Substitution Principle Zasada podstawiania Liskov Właściwośd opisana w sposób: Jeśli dla każdego obiektu o1 typu S istnieje obiekt o2 typu T taki, że każdy program P zdefiniowany dla T zachowuje się tak samo jeśli o1 zastąpimy o2 oznacza to, że S dziedziczy po T. Uh?????
iskov Substitution Principle Zasada podstawiania Liskov Druga próba? Metody które używają wskaźników lub referencji do klasy bazowej powinny mied możliwośd użycia klas dziedziczących bez wiedzy o tym że używają klasy dziedziczących
iskov Substitution Principle Zasada podstawiania Liskov Trzecia próba? LSP w przykładach: public void RenderCell(int rinx, int cinx, CellFormatArgs args) { ICell cell = fetchcell(rinx, cinx); if(cell is CellPrice) { //render the price cell } else if (cell is CellRate) { //render the ratecell } else if (cell is CellDouble) { //render the double cell } }
Czy kwadrat jest prostokątem? public class Rectangle { public virtual double Width { get; set; } public virtual double Height { get; set; } } public void TestR(Rectangle rct) { rct.width =5; rct.height =5; Assert.AreEqual(20, rct.width * rct.height); } public class Square: Rectangle { public override double Width { set{ base.height = value; base.width =value; } } public override double Height { set{ base.height = value; base.width =value; } } }
Wygląda jak kaczka, kwacze jak kaczka, ale potrzebuje baterii Prawdopodobnie masz złą abstrakcje
SOLI
ependency Inversion Principle Zasada odwracania zależności Przylutujesz lampę bezpośrednio do gniazdka w ścianie?
ependency Inversion Principle Zasada odwracania zależności Moduły wysokiego poziomu nie powinny zależed o modułów niskiego poziomu. Oba powinny zależed od abstrakcji. Abstrakcja nie powinna byd zależna od detali. Detale powinny byd zależne od abstrakcji.
public void Copy(DevType dev) { while(true){ int input = console.read(); if(input == -1) break; char inputchar = (char)input; if(dev == DevType.Printer) writeprinter(inputchar); else writedisk(inputchar); } } public void Copy(Reader reader, Writer output) { while(true) { int input = reader.read(); if(input == -1) break; output.write(input); } }
SOL D
nterface Segregation Principle Zasada segregacji interfejsów Gdzie mam to włożyd?
nterface Segregation Principle Zasada segregacji interfejsów Klienci nie powinni byd zmuszani do zależności od interfejsów których nie używają
Źródła Zasady SOLID: http://butunclebob.com/articles.unclebob.principlesofood Blog Rober C. Martin: http://blog.objectmentor.com/ Źródło części obrazków w prezentacji: http://www.lostechies.com/blogs/derickbailey/archive/2009/ 02/11/solid-development-principles-in-motivationalpictures.aspx
Michał Brzozowski http://twitter.com/brzozow brzozow@gmail.com michal.brzozowski@pl.abb.com
Oceo moją sesję Ankieta dostępna na stronie www.mts2009.pl Wygraj wejściówki na następny MTS!
2009 Microsoft Corporation. Wszelkie prawa zastrzeżone. Microsoft, Windows oraz inne nazwy produktów są lub mogą byd znakami towarowymi lub zastrzeżonymi znakami towarowymi firmy Microsoft w Stanach Zjednoczonych i innych krajach. Zamieszczone informacje mają charakter wyłącznie informacyjny. FIRMA MICROSOFT NIE UDZIELA ŻADNYCH GWARANCJI (WYRAŻONYCH WPROST LUB DOMYŚLNIE), W TYM TAKŻE USTAWOWEJ RĘKOJMI ZA WADY FIZYCZNE I PRAWNE, CO DO INFORMACJI ZAWARTYCH W TEJ PREZENTACJI.