;; The first three lines of this file were inserted by DrRacket. They record metadata ;; about the language level of this file in a form that our tools can easily process. #reader(lib "htdp-beginner-reader.ss" "lang")((modname list-of-teams-example) (read-case-sensitive #t) (teachpacks ()) (htdp-settings #(#t constructor repeating-decimal #f #t none #f () #f))) ; Ian Barland ; http://www.radford.edu/~itec380/2016summerIII-ibarland/Homeworks/hw03b.html ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; #1 - `team` data type ;;;;;;;;;;;;;;;;;;;;;;;;;; ; Design recipe step #1: Data definition: In our code, ; a `team` is: ; (make-team [non-empty string] [real] [real]) (define-struct team (name offense defense)) ; Design recipe step #2: Examples of data: (define warriors (make-team "Warriors" 93 85)) (make-team "Ducks" 25 70) (make-team "Quacks" 0.3 91) ; Design recipe step #3: Template for *any* function handling teams: ; func-for-team : team -> ... (define (func-for-team a-team) (... (team-name a-team) (team-offense a-team) (team-defense a-team))) ; Um, just a reminder: there is NO `cond` in that template, ; because we have a struct: we're not asking IF we were given ; a team-name or a team-offense; we KNOW were were given them! ; So any function handling teams will extract the fields ; (and then do something function-specific with them). ;;;;; steps per-function: for `team>?` ;;;; ; Design recipe step #4: Test cases (check-expect (team>? warriors (make-team "Ducks" 25 70)) #true) (check-expect (team>? (make-team "Ducks" 25 70) (make-team "Warriors" 93 85)) #false) (check-expect (team>? (make-team "Ducks" 25 70) (make-team "The Geesers" 25 70)) #false) (check-expect (team>? (make-team "Warriors" 93 85) (make-team "Quacks" 0.3 91)) #true) (check-expect (team>? (make-team "Quacks" 0.3 91) (make-team "Warriors" 93 85)) #false) (check-expect (team>? (make-team "Warriors" 93 85) (make-team "B" 93 4)) #false) (check-expect (team>? (make-team "Warriors" 93 85) (make-team "C" 85 90)) #false) (check-expect (team>? (make-team "Warriors" 93 85) (make-team "C" 84 93)) #false) (check-expect (team>? (make-team "Warriors" 93 85) (make-team "C" 85 93)) #false) ; Design recipe step #5: Signature, header, purpose ; team>? : team, team -> boolean ; Is one team strictly better than another? ; (define (team>? team1 team2) ; Design recipe step #7: complete the function's body. (and (> (team-offense team1) (team-defense team2)) (> (team-defense team1) (team-offense team2)))) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; #2 - space invader object design ;;;;;;;;;;;;;;;;;;;;;;;;;; #| Objects involved with a space-invaders game would be: - the player's cannon - just an x-coordinate (of center? what units?) - since the y-coordinate and its image are invariant, no other info needed. - a shield/block [optional for our version] - x,y coordinate (of center? what units?) - an alien: - x and y coordinate (in pixels, from upper-left corner of screen); - if all aliens will be drawn the same, then no add'l fields - The full arcade version would have different images and point-values. But since each "subspecies" would have its own invariant image and point-value, really there'd be a sub-type for each subspecies, rather than have those field for all aliens. - if all aliens are marching left/right in unison, then their direction/speed is invariant, so it would NOT be a field replicated inside each object. (In O.O. we'd have a "class field" to represent this (java term: "static")). - a bullet: - x and y coordinate - a y-direction (+1 or -1) -- this lets the same object represent both the missiles fired - since the size/color of a bullet is invariant, no other fields. (If you had different size color/bullets for the player and the aliens, then you'd have subtypes for each such bullet-type.) - a score [optional for our version] - just a non-negative number ---- The full game will have additional types: - list-of-alien - list-of-bullet - list of blocks (optional for us) |# ; A cannon is: ; a real number ; (Note that this data definition doesn't do much, but it does let us label ; functions that take/return cannons a bit more descriptively. ; But you do need to mention somewhere, that a single number is being used ; to represent the cannon.) ; An alien is: ; (make-alien [real] [real]) ; `x`,`y` is the location of the CENTER of the alien, in pixels, from the upper-left corner ; (usual computer-graphics convention coordinates increasing as you go to the right and down). (define-struct alien (x y)) ; Examples: (make-alien 50 70) (define a0 (make-alien 0 -2)) #| Java: class Alien { double x,y; // the center of the alien, in pixels from upper-left. Alien( double _x, double _y ) { this.x = _x; this.y = _y; } void test() { new Alien(50,70); Alien a0 = new Alien(0,-2); } } |# ; A bullet is: ; (make-bullet [real] [real] [real]) (define-struct bullet (x y dy)) ; x,y are the center's coordinate in pixels. ; dy is how fast the bullet is traveling up/down (up for cannon-bullets, down for alien-bullets). ; likely +1/-1 times some suitable constant. ; NOTE: you could also use ints for the coordinate-locations, if your physics doesn't ; Fortunately, the drawing-library we'll use in racket does allow you to specify ; real-numbers as locations (even if the drawing might get rounded to the ; best-possible-representation of the underlying model). ; Also, the fact that the coordinate system in computer graphics is from upper-left toward lower-right ; can be omitted -- it is the widespread default, so it can be assumed. But mentioning that the ; units are in pixels is still helpful, since another convention might be that the screen always goes ; from (0,0) to (1,1) and is invariant under re-sizing the gui. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; #| ============= functions involving lists ============= (functions with recursive data-definition) Sample: 1. Give a data-defn for list-of-Teams 2. give examples 3. give template Write a function: best-offense : list-of-teams -> number 4. test-cases 5. purpose, signature, header, stub 6. copy template and fill in inventory-with-values 7. complete the function 8. watch your tests pass |# ; A list-of-Teams is: ; - '() OR ; - (cons [Team] [list-of-Teams]) ; Examples of list-of-Teams '() (cons (make-team "Ducks" 25 70) '()) (cons (make-team "Quacks" 0.3 91) (cons (make-team "Ducks" 25 70) '())) (cons warriors (cons (make-team "Quacks" 0.3 91) (cons (make-team "Ducks" 25 70) '()))) (cons (make-team "Bears" 10 10) (cons (make-team "Lions" 1 1) '())) ; template for list-of-Teams (define (func-for-loTeams some-teams) (cond [(empty? some-teams) ...] [(cons? some-teams) (... (first some-teams) ... (func-for-loTeams (rest some-teams))) ])) ;;;; step #4 -- test cases for `best-offense`: (check-expect (best-offense '()) 0) (check-expect (best-offense (cons (make-team "Ducks" 25 70) '())) 25) (check-expect (best-offense (cons (make-team "Quacks" 0.3 91) (cons (make-team "Ducks" 25 70) '()))) 25) (check-expect (best-offense (cons warriors (cons (make-team "Quacks" 0.3 91) (cons (make-team "Ducks" 25 70) '())))) 93) (check-expect (best-offense (cons (make-team "Quacks" 0.3 91) (cons warriors (cons (make-team "Ducks" 25 70) '())))) 93) ; best-offense : list-of-Teams -> number ; Return the highest offense of any team in the list, or 0 if the list is empty. ; (define (best-offense some-teams) (cond [(empty? some-teams) 0] [(cons? some-teams) (max (team-offense (first some-teams)) (best-offense (rest some-teams)))]))