CS51 - Spring 2010 - Lecture 13
An infinite number of mathematicians walk into a bar. The first one orders a beer. The second orders half a beer. The third, a quarter of a beer. The bartender says "You're all idiots", and pours two beers.
quiz: exercise 12.1.9
what is structural recursion?
- defining an object with respect to a smaller object of that same type
revisit target and broccoli
- what is the base case and why do we need it?
- base case/class ends the recursion
- if we didn't have it, we continue to recurse indefinitely
designing recursive programs
- describe the recursion in words...this should suggest the recursive and base classes, as well as the instance variables in each
- define an interface with all the methods that both the base and recursive cases must implement
- define the class(es) representing the base case(s)
- define the constructor(s) for the recursive class(es). The recursive calls in the constructor should create objects that are simpler than the one currently being constructed. In particular, eventually you should hit the base case.
- write each method in the recursive class(es) using the assumption that the method will work correctly on the simpler objects referred to by the instance variables
show
SimpleRecScribbler demo
- this is the same basic scribbler that we saw before, but now we can drag the previous scribble
- how does the basic version of scribble work?
- onMouseDrag we draw a new line from wherever we were last time to where we are now
- can we use recursion here?
- describe the recursion in words
- a "Scribble" is a line connected to another Scribble
- what things do we want the Scribble to be able to do?
- move
- contains
- look at ScribbleIfc interface in
SimpleRecScribbler code
- what will the base case be?
- remember our "recursive" definition is that a scribble is a line, followed by another Scribble
- the base case is just an "empty" scribble
- look at EmptyScribble class in
SimpleRecScribbler code
- what does the constructor for Scribble look like?
- this is a little trickier this time
- we're not constructing the drawing ourselves, but need the user's input to construct it
- constructor needs to take a line and a scribble and we just save that information
- write the methods?
- contains
- move
- look at NonEmptyScribble class in
SimpleRecScribbler code
how do we construct a complete scribble?
- for all the other ones, we've been constructing it from the top down, i.e. from the largest thing to the smallest (i.e the base case)
- here, we're going to construct it from the bottom (base case) up
- as the user drags
- we keep track of the current scribble
- when we draw a line, we also add that line onto our current scribble
- look at
SimpleRecScribbler code
- always start with the empty scribble
- link in the new lines as we draw them
show
DraggableChain demo
- similar to the scribbler demo, except now we've replaced a line with a ball
- describe the recursion in words
- a "chain" is a FilledOval connected to a chain
- what things do we want the chain to be able to do?
- move
- contains
- what will the base case be?
- an EmptyChain
- look at EmptyChain class in
DraggableChain demo
- what does the constructor look like?
- FilledOval
- ChainIfc
- notice that like the scribble example, another class constructs the FilledOval. The Chain class is just used to keep track of the items so we can manipulate them
- methods
show
ChainReaction demo
- like before, every time I click a new ball is added to the end of our chain
- every time I move the mouse out of the window, the balls all move to the right in an animated fashion
- how can we make this happen?
- idea 1: create an AnimatedBall class that extends ActiveObject and then create a chain of AnimatedBalls rather than FilledOvals
- ActiveObjects are always animated
- we'd have to figure out some way to pause and unpause them
- getting the timing right from ball to ball would also be challenging
- idea 2: each time we want to move the chain over, we create a new ActiveObject to handle the animation of moving the balls over once
- the timing is done in one class, so we can move the balls in sequence
- just create a new object to move them each time the mouse exits the window
- what would this class, we'll call it ChainAnimater, look like?
- extends ActiveObject
- need to take in a chain
- in the run method
- for each ball:
- animate the movement to the right
- nested while loops
- one to iterate over the balls
- one (an inner one) to animate the movement of the ball
- we can use our same recursive definition of a Chain as before
- a "chain" is a FilledOval connected to a chain
- how can we describe the animation process recursively?
- as long as our ball list has remaining balls, animate the ball at the front of the list
- then, animate the rest of the list
- what things do we want the ball list to be able to do?
- The key place we'll be using this is in the ChainAnimator
- need to be able to get the FramedOval that's at the front of the chain (so we can animate it)
- need to be able to get the rest of the chain
- need to be able to tell if there are any remaining balls
- look at ChainIfc class
- getFirst()
- getRest()
- isEmpty()
- what will the base case be?
- isEmpty() will return true;
- look at EmptyChain
- what does the constructor look like?
- constructor doesn't change
- what about the methods?
- getFirst() just returns the FramedOval
- getRest() the recursive portion
- isEmpty() returns false
look at
ChainReaction code
- ChainReaction
- onMousePress we append another ball on to the beginning of the ball list
- onMouseExit creates a new ChainAnimator
- ChainAnimator
- iterates over each of the balls in the outer while loop
- ballList = ballList.getRest() moves it along to the next ball
- inner while loops animates the movement of a ball a first distance
these two examples (Scribble and ChainReaction) are both examples of what are called linked lists
look at Lab 7