Скачать презентацию Hints — Mandatory 2 Strategies Learning Скачать презентацию Hints — Mandatory 2 Strategies Learning

8014098863e1a65976aa15272df80f3f.ppt

  • Количество слайдов: 69

Hints - Mandatory 2 / Strategies Hints - Mandatory 2 / Strategies

Learning. . . http: //blogs. hbr. org/johnson/2012/09/throw-your-life -a-curve. html Aah, det giver da lidt Learning. . . http: //blogs. hbr. org/johnson/2012/09/throw-your-life -a-curve. html Aah, det giver da lidt mening! Jeg fatter ikke en bjælde!? ! CS@AU H B Christensen 2

TDD being standard? Henrik Bærbak Christensen 3 TDD being standard? Henrik Bærbak Christensen 3

Fake-it is a strong tool . . . To help new abstractions into development Fake-it is a strong tool . . . To help new abstractions into development as part of keeping focus on something else. Check out the screencast on weekplan: unitmove-faked. Feature: move. Unit – Require a data structure for storing units in the world, so a World role is faked to keep focus on the move. Unit method. . . Henrik Bærbak Christensen 4

Java 8 and Lambda expressions Java 8 (finally) introduced lambda’s – Inline code blocks Java 8 and Lambda expressions Java 8 (finally) introduced lambda’s – Inline code blocks Actually, the @Functional. Interface is automatically applied by the compiler. Henrik Bærbak Christensen 5

Sprint 2 Functional requirements – Develop and maintain 4 variants • Beta: Alternative winning Sprint 2 Functional requirements – Develop and maintain 4 variants • Beta: Alternative winning and aging algorithm • Gamma: Allows some units to do an action • Delta: Alternative world layout – All are variants of Alpha. Civ Real/Architectural requirements – Use Alpha. Civ tests to support refactoring Game. Impl into a compositional design (strategy pattern/3 -1 -2) – Develop the delegates that introduce the new variant behaviour Henrik Bærbak Christensen 6

Deliveries Basically – The code (of course! The truth is in the code!) – Deliveries Basically – The code (of course! The truth is in the code!) – Refactoring screencast (process) • Use the ‘refactoring rhythm’ of TDD and unfold the process in your video to show it to your TA – Composional screencast (explain) • Navigate your code while explaining to the TA which code fragments serve which roles in Strategy/compositional design and how they came about from applying 3 -1 -2 – ”We ‘encapsulated’ a Winner. Strategy (3) in this interface (1) which has method … Then we can make a delegate implemenation (this code here, which is then principle 2). The Game is constructed here where you can see we configure it to be Beta. Civ… Now we run our tests…” Henrik Bærbak Christensen 7

Deliveries And – Design: Make a UML diagram of your resulting design, highlighting the Deliveries And – Design: Make a UML diagram of your resulting design, highlighting the compositional structure… • Ala… Henrik Bærbak Christensen 8

Study Café discussions “Your specification of feature X in Hot. Civ is unclear, Henrik!” Study Café discussions “Your specification of feature X in Hot. Civ is unclear, Henrik!” – Yes. Face it – this is how real life is! – Agile method’s answer: Ask the customer! • “on-site customer” / “product owner” My answer is always – I do not really care about functionality • This is not an algorithm course! – d. Soft. Ark is about flexible reliable design • This is a software architecture course So: pick the simplest algorithmic solution that fit the requirement and spend the time on a flexible and reliable design Henrik Bærbak Christensen 9

Best way to code. . . Grab yourself a copy of Uncle Bob’s book Best way to code. . . Grab yourself a copy of Uncle Bob’s book ! Ask on the web board! And read the comments – Best way to structure packages ? • Good question Henrik Bærbak Christensen 10

Conditionals are hard to read!!! Is this code correct for move. Unit If it Conditionals are hard to read!!! Is this code correct for move. Unit If it is hard to write then – It is probably buggy! – You yourself cannot understand it in two weeks – Bjarne will never be able to understand it • Beware when he comes around and “fixes” it!!! Henrik Bærbak Christensen 11

Real example. . . Real example. . .

Remedy 1: Fail-fast Think which conditions allows me to bail out immedately? Henrik Bærbak Remedy 1: Fail-fast Think which conditions allows me to bail out immedately? Henrik Bærbak Christensen 13

Remedy 2: Take small steps Divide and conquer. Take small steps. Henrik Bærbak Christensen Remedy 2: Take small steps Divide and conquer. Take small steps. Henrik Bærbak Christensen 14

Often more analyzable to ‘patch’ That is: a) Fill entire structure with common element Often more analyzable to ‘patch’ That is: a) Fill entire structure with common element b) Patch the exceptions Plains Henrik Bærbak Christensen 15

Side note Simplicity – Maximize work not done Remember – A GUI handles a Side note Simplicity – Maximize work not done Remember – A GUI handles a lot of cases for us so it is actually wrong to implement code that handles situations that violate preconditions! And to make test cases for it! Henrik Bærbak Christensen 16

Fake-it till you make it Fake-it is a wonderful pattern but should be removed Fake-it till you make it Fake-it is a wonderful pattern but should be removed and replaced by proper general algorithms as soon as possible!!! Anti example – We must develop: int sum(x, y) – Iteration 1: • assert. Equals( 3, obj. sum(1, 2) ); • int sum(int x, int y) { return 3; } – Iteration 2: • assert. Equals( 5, obj. sum(3, 2) ); • int sum(int x, int y) { if (x==3 && y==2) return 5; else return 3; } Henrik Bærbak Christensen This is a catastrophe and 17 has nothing to do with TDD!

Exercise: Why is this unfortunate? In Game. Impl: Henrik Bærbak Christensen 18 Exercise: Why is this unfortunate? In Game. Impl: Henrik Bærbak Christensen 18

Exercise: Why is this unfortunate? In Game. Impl: Henrik Bærbak Christensen 19 Exercise: Why is this unfortunate? In Game. Impl: Henrik Bærbak Christensen 19

The problem. . . A theme of much code last years: You try to The problem. . . A theme of much code last years: You try to introduce strategies (compositional) But wrap them in param. /polym. designs Result: All liabilities from both methods – Inflexibility and code bloat from the if (. . . ) { } / subclass – And all the extra classes and interfaces from Composition Henrik Bærbak Christensen 20

Gamma. Civ and Unit. Action Gamma. Civ and Unit. Action

Gamma. Civ and 36. 11 Gamma. Civ: Settler and Archer action – destroy settler, Gamma. Civ and 36. 11 Gamma. Civ: Settler and Archer action – destroy settler, create city ; fortify archer Two Solutions / polymorphic or compositional – Who/What (model focus / polymorphic): • Who: The settler ’does something’ • What: create city (and kill itself? ); modify archer def. strength – What/Who (behavioral focus / compositional): • What: Encapsulate ’unit action’ = algorithm = Strategy • Who: Game’s ’perform. Unit. Action. At’ delegates. . . Henrik Bærbak Christensen 22

Settler Action, Polymorphic method on Unit Game. Impl. perform. Action() { u. action(); } Settler Action, Polymorphic method on Unit Game. Impl. perform. Action() { u. action(); } Cohesion – High: what a settler /archer does; but unit now ”knows a lot” Coupling – – City : Unit now coupled to City (”must say new Std. City()”); World: Either direct access or ask Game to put city Destroying: Cannot be done, must ask Game Making settlers: abstract factory to make subtype outside Hot. Civ framework (which contain a switch)– OR a switch on unit type (no support for adding types later) Henrik Bærbak Christensen 23

Polymorphic Henrik Bærbak Christensen 24 Polymorphic Henrik Bærbak Christensen 24

Settler Action, Compositional Strategy on perform. Unit. Action. At Henrik Bærbak Christensen 25 Settler Action, Compositional Strategy on perform. Unit. Action. At Henrik Bærbak Christensen 25

Settler Action, Compositional Strategy on perform. Unit. Action. At Cohesion: – High: Gamma. Action. Settler Action, Compositional Strategy on perform. Unit. Action. At Cohesion: – High: Gamma. Action. Strategy is highly focused; but potentially knows many unit types (parametric switching) but in the delegate!!! Coupling: Must know – Unit (or just the type) – Game • Or rather methods to create city and destroy unit • Or know city + world – Cities’ unit making: just ”new Unit. Impl(type); ” - done – Gamma. Action. Strategy: has a switch on unit types. . . Henrik Bærbak Christensen 26

Settler Action, Score Board Which is the better? Compositional scores best. . . Benefit Settler Action, Score Board Which is the better? Compositional scores best. . . Benefit – Lower coupling (No Unit->”Others” coupling) – Easier to create Units (all are alike except type string) • Avoid need for factory system when it is a framework – Unit destroying has to be made in Game anyway – Easy to configure Game with new actions strategies – Polymorphic must have a switch anyway! (just in another place) Liabilities – Action. Strategy will contain a type switch • Parameterized variance but in ’external’ code. – May become ’blob-code’, difficult to reuse. . . Henrik Bærbak Christensen 27

Reuse of Strategies Note that adding, say, a Chariot unit type can be made Reuse of Strategies Note that adding, say, a Chariot unit type can be made purely by addition in compositional case. . . – Compositional: add a ”XYZAction. Strategy” which • If (type. equals(”Chariot”)) {. . . } • else { • [D]. perform. Unit. Action. At(p); • } – Where [D] is either • super in case new strategy inherits from the old one • delegate in case we do composition –Which is actually the decorator pattern – Polymorphic: Add Chariot. Unit + modify city code Henrik Bærbak Christensen 28

Keep your Test code clean! Do not duplicate Alpha. Civ test cases in Beta. Keep your Test code clean! Do not duplicate Alpha. Civ test cases in Beta. Civ Only include the Beta specific test cases – Or better – unit test the Winner. Strategy. . . Henrik Bærbak Christensen 29

Delegate Truely! I say – son. take. Garbage. To. Can() I do not say Delegate Truely! I say – son. take. Garbage. To. Can() I do not say – – – son. pick. Up. Garbage(); son. walk. To. Can(); son. open. Can. Lid(); son. put. Garbage. Into. Can(); son. walk. To. House(); Exercise: Why is second version problematic? Henrik Bærbak Christensen 30

Delegate Truely Do not tell the strategy the invidiual steps! Let the strategy take Delegate Truely Do not tell the strategy the invidiual steps! Let the strategy take its responsibility! – layout. Strategy. layout. World( tile. List, city. List, unit. List ); – Or similar. . . Henrik Bærbak Christensen 31

More Fun stuff from trenches Henrik Bærbak Christensen More Fun stuff from trenches Henrik Bærbak Christensen

Beta Winner – General or not? Cities in Alpha. Civ, how? – – Matrix Beta Winner – General or not? Cities in Alpha. Civ, how? – – Matrix of City Objects? List of City Objects? Matrix of Tile objects having reference to City object? World class? City red. City; blue. City; ? ? ? Beta Winner: All cities conquered – But Beta is Alpha which has only two cities? ? ? – A) Iterate world, ensure all cities owned by player X – B) red. City. get. Owner() == blue. City. get. Owner() ? Henrik Bærbak Christensen 33

Maximize work not done Beta. Civ Winner – First to conquer all cities in Maximize work not done Beta. Civ Winner – First to conquer all cities in the world But Beta. Civ augments Alpha. Civ in which no cities can be produced! – Winner algo: { if owner(c 1) == owner(c 2) return true; } What if we later can produce cities? – Then we must refactor winner algorithm What if we never will be requested to produce cities? – The we have saved valuable time now

Dependency Injection Merits – All variant handling code in cohesive object But think Abstract. Dependency Injection Merits – All variant handling code in cohesive object But think Abstract. Factory handles it more elegant Henrik Bærbak Christensen 35

Variability is variable (3) Encapsulate what varies – Or Cutting the cake properly. It Variability is variable (3) Encapsulate what varies – Or Cutting the cake properly. It is difficult Henrik Bærbak Christensen 36

Multiple Maintenance Source code copy. Easy but costly! – Here comes the Chariot! Henrik Multiple Maintenance Source code copy. Easy but costly! – Here comes the Chariot! Henrik Bærbak Christensen 37

Null. Object Avoid the if ( strategy != null ) pit fall: if(unit. Action. Null. Object Avoid the if ( strategy != null ) pit fall: if(unit. Action. Strategy == null) return; Henrik Bærbak Christensen 38

Do not dispair TA presented a ‘nice solution’. . . Morale: We often over-engineer Do not dispair TA presented a ‘nice solution’. . . Morale: We often over-engineer Henrik Bærbak Christensen 39

Previous Years Henrik Bærbak Christensen Previous Years Henrik Bærbak Christensen

Review your UML ”The blender is in the frog” – Structure of sentences is Review your UML ”The blender is in the frog” – Structure of sentences is important! Dependency – Rather vague – Use assoc/aggr istead Unit-Game. Impl – The wrong way around Henrik Bærbak Christensen 41

Design Pitfalls Writing simple algorithms Henrik Bærbak Christensen Design Pitfalls Writing simple algorithms Henrik Bærbak Christensen

”Accessor becomes Mutator” trap I have seen this many times As our code only ”Accessor becomes Mutator” trap I have seen this many times As our code only calls ‘get. Winner’ once per round, it seems like a nice place to handle the round increment. What is the major problem in that? Henrik Bærbak Christensen 43

Cohesive roles Role well defined? Encapsulate what varies? Henrik Bærbak Christensen 44 Cohesive roles Role well defined? Encapsulate what varies? Henrik Bærbak Christensen 44

Cohesive roles Problem: – move. Unit is same for all game variants – perform. Cohesive roles Problem: – move. Unit is same for all game variants – perform. Action is not Thus – Variable + common behaviour in same unit => one cannot change without other affected Group's solution – Gamma inherits Alpha Henrik Bærbak Christensen 45

Minor 'not so good' I do not like the 'set. Game'. I would prefer Minor 'not so good' I do not like the 'set. Game'. I would prefer – perform. Action(game, pos); – (I. e. Pass game instance every time. ) Why? Henrik Bærbak Christensen 46

Readability? Positive: – Comments! Negative: – Code duplication! – Nesting level. Code duplica tion Readability? Positive: – Comments! Negative: – Code duplication! – Nesting level. Code duplica tion leads to d duplication bug Exercise: Fin bugs! Henrik Bærbak Christensen 47

My refactoring Note: The tile type bugs are kept. Henrik Bærbak Christensen 48 My refactoring Note: The tile type bugs are kept. Henrik Bærbak Christensen 48

Which would you prefer to review ? Henrik Bærbak Christensen 49 Which would you prefer to review ? Henrik Bærbak Christensen 49

More of the same. . . More of the same. . .

Writing simple algorithms. . . How do I write 'simple' algorithms like move. Unit? Writing simple algorithms. . . How do I write 'simple' algorithms like move. Unit? Use C style 'bail out': if (x) return; Simplicity: – Take the simplest first (requires fewest info) – Intro more info as you need it (only then!) – Write the comments first (keep focus!)

Writing simple algorithms… Try hard to avoid – Conditionals with too many elements • Writing simple algorithms… Try hard to avoid – Conditionals with too many elements • If ( cond 1 && cond 2 || cond 3 ) – If you cannot avoid it, then unfold the conditions • Boolean no. Unit. On. From = game. get. Unit. At(p) == null; • Boolean to. Cannot. Be. Moved. To =. . . ; • If ( no. Unit. On. From || to. Cannot. Be. Moved. To ) return false; – Use the C style bail-out, not Pascal style nested ifs • If (bad) return false; • If (! bad ) {. . . } else { return false; } Simple Complex

Package structure Common and variant code Common = code that is executed in all Package structure Common and variant code Common = code that is executed in all variants of the final delivered systems – Game. Impl Variant = code (delegate) that is executed in one or a few variants Henrik Bærbak Christensen 53

More State Pro: Learning exercise Con: Overkill!!! Henrik Bærbak Christensen 54 More State Pro: Learning exercise Con: Overkill!!! Henrik Bærbak Christensen 54

Misc. . . Why not just use the Alpha strategy? Henrik Bærbak Christensen 55 Misc. . . Why not just use the Alpha strategy? Henrik Bærbak Christensen 55

Unit versus System test Important to test the game because it is what the Unit versus System test Important to test the game because it is what the ’costumer’ pays for No test that ’move’ method will not move the unit! Henrik Bærbak Christensen 56

The mutable interface danger Pro: – Better to directly set the testable condition (set The mutable interface danger Pro: – Better to directly set the testable condition (set owner of city to blue) than a lot of (defect-potential) code to get the game into this situation Con: – Really really bad to introduce a mutator method in City interface directly Henrik Bærbak Christensen 57

Unit/Integeration testing Many groups test Aging. Strategy through Game – That is: one zillion Unit/Integeration testing Many groups test Aging. Strategy through Game – That is: one zillion ”end. Of. Turn()” Remember Unit testing – – assert. Equals( -4000, as. calc. Age(0)); assert. Equals( -100, as. calc. Age(39)); assert. Equals( -1, as. calc. Age(40)); Etc. Henrik Bærbak Christensen 58

UML Brush up Review class and sequence diagrams from your old books Henrik Bærbak UML Brush up Review class and sequence diagrams from your old books Henrik Bærbak Christensen 59

Software View Think roadmap! – Avoid method names Class Navigability Interface Still – take Software View Think roadmap! – Avoid method names Class Navigability Interface Still – take care no to overload with detail. . . Much different from conceptual view. Henrik Bærbak Christensen Realization/impl 60

Behavior Sequence diagrams Participant (object) – Describe a single scenario Timeline Example – Buy Behavior Sequence diagrams Participant (object) – Describe a single scenario Timeline Example – Buy ticket sequence creation message return self-call Henrik Bærbak Christensen activation 61

Frames Henrik Bærbak Christensen 62 Frames Henrik Bærbak Christensen 62

Src-Code-Copy No no no. . . – Do not make a copy of Alpha. Src-Code-Copy No no no. . . – Do not make a copy of Alpha. Civ to begin working on Beta. Civ etc. You can and will see this in practice, but. . . This is not the intended learning outcome Henrik Bærbak Christensen 63

Clean Code That Works . . . That Works is not enough. . . Clean Code That Works . . . That Works is not enough. . . Clean code means – Refactoring you existing code • Review coupling and cohesion – Removing duplicated code – Review method and variable names • Do they convey the proper meaning? – Create classes / packages • Move methods / classes into better named software units Henrik Bærbak Christensen 64

One Strategy to Rule Them All. . . Henrik Bærbak Christensen 65 One Strategy to Rule Them All. . . Henrik Bærbak Christensen 65

Beware What will happen when. . . – I have three different winner conditions Beware What will happen when. . . – I have three different winner conditions – I have four different aging strategies –. . . And eight different configurations of unit actions? Combinatorial explosion of subclasses. . . Henrik Bærbak Christensen 66

The Worst of Two worlds. . . Henrik Bærbak Christensen 67 The Worst of Two worlds. . . Henrik Bærbak Christensen 67

There Must Be a Switch Somewhere! However, it is important where it is! – There Must Be a Switch Somewhere! However, it is important where it is! – Inside game • You cannot add new variants expect by change by modification – In the main method /configuration code • All the Hot. Civ code can be frozen into a JAR file that is not going to be changed! How often have you added a clause to a switch inside Java Swing? Henrik Bærbak Christensen 68

Getting Info Into the Strategies How does Winner. Strategy know anything? ? ? – Getting Info Into the Strategies How does Winner. Strategy know anything? ? ? – Review Finn’s note on the web site. . . Internal datastructure (like ’array of tile/city’) – Sending internal data structure of Game. Impl to the strategy • Higher coupling, cannot change datastructure later, no encapsulation. . . – Double references • Winner. Strategy s = new Beta. Winner. Strategy(game) • Game game = new Game. Impl(s); • Better: return get. Winner(this) in Game. Impl. . . Henrik Bærbak Christensen 69