# Recursion Lab Solutions # recursiveTurtles.py from turtle import * # Tests are at the bottom in the run function. # Provided helper function # You can, but don't need to, change anything in this function def intializeTurtle(): ''' Initialize turtle on Canvas before drawing ''' setup(800, 600) # Create a turtle window reset() # Show turtle window and turtle pencolor('black') # You can change the pencolor # Set the speed; 0=No animation, 1=slowest, 6=normal, 10=fast, etc. speed(100) # You can change this to vary the speed of your turtle # Turtle, by default, starts roughly in center of canvas pu() # Start the turtle in the bottom left corner setx(-200) sety(-200) pd() # Magical statements to make turtle window come to top of screen getscreen()._root.attributes('-topmost', True) getscreen()._root.attributes('-topmost', False) # ------------------------------------ # Task 1 # ------------------------------------ # Provided function. Version A: No loops, no recursion def square(length): ''' Draws a square of size length maintains heading and position invariant ''' fd(length) lt(90) fd(length) lt(90) fd(length) lt(90) fd(length) # back to starting location lt(90) # heading in same direction as start # Provided function. Version B: For loop, no recursion def square(length): ''' Draws a square of size length maintains heading and position invariant ''' for i in range(1,5): # or for i in range(4) fd(length) lt(90) # ------------------------------------ # Task 2 # ------------------------------------ def row(number, size): ''' Recursively draw a row of squares (like asteriskLine), maintains a position invariant ''' if (number > 0): square(size) fd(size) row(number-1,size) # recursive call bk(size) # maintain position invariant # ------------------------------------ # Task 3 # ------------------------------------ def spacedRow(number, size): ''' Recursively draw a row of squares with a constant space in between squares and maintians a posiion invariant ''' if (number > 0): square(size) # move to position to draw the next one pu() fd(size + size/4) pd() spacedRow(number-1,size)# recursive call # move back to original starting position (maintain position invariant) pu() bk(size+ size/4) pd() # ------------------------------------ # Task 4 # ------------------------------------ def decreasingRow(number, size): ''' Recursively draw a row of squares that get progressively smaller by 1/2 each time and maintains a position invariant ''' if (number > 0): square(size) fd(size) decreasingRow(number-1,size/2.)# recursive call bk(size) # maintain position invariant # ------------------------------------ # Task 5 -- omitted in Spring 19, but good extra practice! # ------------------------------------ def nestedSquares(number, size): ''' Recursively draw nested squares that get progressively smaller by 1/2 each time anchored in the lower left corner ''' if (number > 0): square(size) nestedSquares(number-1,size/2.)# recursive call # ------------------------------------ # Task 6 # ------------------------------------ def diagonal(number, size): ''' Recursively draw a row of squares that get progressively smaller by 1/2 each time where each successive square is anchored on the upper right corner of the previous square. Maintains a position invariant ''' if (number > 0): square(size) # move to position to draw next one fd(size) lt(90) fd(size) rt(90) diagonal(number-1,size/2.)# recursive call bk(size) # move back: maintain position invariant -- this block of 4 lines undo the block of 4 lines (fd, lt, fd, rt) before the recursive call lt(90) bk(size) rt(90) # ------------------------------------ # Task 7 # ------------------------------------ def superDiagonal(number, size): ''' Recursively draw a row of squares that get progressively smaller by 1/2 each time where each successive square is anchored on the upper right corner of the previous square and the upper left corner of the previous square ''' if (number > 0): square(size) # back at lower left starting point # get into position for recursive call fd(size) lt(90) fd(size) rt(90) # recursive call for diagonal stemming from upper right corner # Note the 2. allows for more precision, e.g. if size is odd # then we get a more accurate half size. superDiagonal(number-1,size/2.) # first recursive call # maintain position invariant by undoing the steps before # the recursive call lt(90) bk(size) rt(90) bk(size) # back at lower left corner, facing East # draw the diagonal in the SouthWest direction lt(180) superDiagonal(number-1,size/2.) # second recursive call rt(180) def run(): intializeTurtle() # Tests #square(100) #row(5, 100) #spacedRow(5, 100) #decreasingRow(5, 100) #nestedSquares(5, 100) diagonal(5, 100) #superDiagonal(5, 100) if __name__ == "__main__": run()