Due by 11:59pm on Tuesday, 10/11

Instructions

Download hw07.zip. The vitamin problems can be found in the `vitamin` directory and the homework problems can be found in the `problems` directory.

You must run `python3 ok --submit` two times: once inside the `vitamin` directory and once inside the `problems` directory.

Submission: When you are done, submit with `python3 ok --submit`. You may submit more than once before the deadline; only the final submission will be scored. Check that you have successfully submitted your code on okpy.org. See Lab 0 for more instructions on submitting assignments.

Using OK: If you have any questions about using OK, please refer to this guide.

Readings: You might find the following references useful:

Vitamin

Question 1: Digits

Implement `digits`, which returns a linked list containing the digits of a non-negative integer `n`.

``````def digits(n):
"""Return the digits of n as a linked list.

>>> digits(0) is Link.empty
True
>>> digits(543)
"""
while n > 0:
n, last = n // 10, n % 10
"*** YOUR CODE HERE ***"
return s``````

Use OK to test your code:

``python3 ok -q digits``

Homework Questions

Question 2: Next Fibonacci Object

Implement the `next` method of the `Fib` class. For this class, the `value` attribute is a Fibonacci number. The `next` method returns a `Fib` instance whose `value` is the next Fibonacci number. The `next` method should take only constant time.

Hint: Assign `value` and `previous` attributes within `next`.

``````class Fib():
"""A Fibonacci number.

>>> start = Fib()
>>> start
0
>>> start.next()
1
>>> start.next().next()
1
>>> start.next().next().next()
2
>>> start.next().next().next().next()
3
>>> start.next().next().next().next().next()
5
>>> start.next().next().next().next().next().next()
8
"""

def __init__(self):
self.value = 0

def next(self):
"*** YOUR CODE HERE ***"

def __repr__(self):
return str(self.value)``````

Use OK to test your code:

``python3 ok -q Fib``

Question 3: Vending Machine

Create a class called `VendingMachine` that represents a vending machine for some product. A `VendingMachine` object returns strings describing its interactions. See the doctest below for examples:

``````class VendingMachine:
"""A vending machine that vends some product for some price.

>>> v = VendingMachine('candy', 10)
>>> v.vend()
'Machine is out of stock.'
>>> v.restock(2)
'Current candy stock: 2'
>>> v.vend()
'You must deposit \$10 more.'
>>> v.deposit(7)
'Current balance: \$7'
>>> v.vend()
'You must deposit \$3 more.'
>>> v.deposit(5)
'Current balance: \$12'
>>> v.vend()
'Here is your candy and \$2 change.'
>>> v.deposit(10)
'Current balance: \$10'
>>> v.vend()
'Here is your candy.'
>>> v.deposit(15)
'Machine is out of stock. Here is your \$15.'

>>> w = VendingMachine('soda', 2)
>>> w.restock(3)
'Current soda stock: 3'
>>> w.deposit(2)
'Current balance: \$2'
>>> w.vend()
'Here is your soda.'
"""
"*** YOUR CODE HERE ***"
``````

Use OK to test your code:

``python3 ok -q VendingMachine``

Question 4: Miss Manners

Create a class called `MissManners` that promotes politeness among our objects. A `MissManners` object takes another object on construction. It has one method, called `ask`. It responds by calling methods on the object it contains, but only if the caller said please first.

We can also compose multiple instances of `MissManners` objects upon each other (see `double_fussy` in doctests). A multilevel `MissManners` object must be politely requested to ask its own `MissManners` object. This continues until we reach the bottom level `MissManners` object.

Hint: Use `getattr` and `hasattr` to access methods using strings.

Hint: Your implementation will need to use the `*args` notation that allows functions to take a flexible number of arguments.

``````class MissManners:
"""A container class that only forward messages that say please.

>>> v = VendingMachine('teaspoon', 10)
>>> v.restock(2)
'Current teaspoon stock: 2'

>>> m = MissManners(v)
'You must learn to say please first.'
'You must deposit \$10 more.'
'Current balance: \$20'
>>> m.ask('now will you vend?')
'You must learn to say please first.'
'Thanks for asking, but I know not how to hand over a teaspoon.'
'Here is your teaspoon and \$10 change.'

>>> double_fussy = MissManners(m) # Composed MissManners objects
'You must learn to say please first.'
'Thanks for asking, but I know not how to deposit.'
'Thanks for asking, but I know not how to please deposit.'
'Current balance: \$10'
"""
def __init__(self, obj):
self.obj = obj

def ask(self, message, *args):
magic_word = 'please '
if not message.startswith(magic_word):
return 'You must learn to say please first.'
"*** YOUR CODE HERE ***"
``````

Use OK to test your code:

``python3 ok -q MissManners``