#This is just a handy function that clears the screen on windows. import os clear = lambda: os.system('cls') class Account(object): """A bank account has a balance.""" interest = 0.02 def __init__(self, starting_balance): self.balance = starting_balance def deposit(self, amount): """Add amount to balance.""" self.balance = self.balance + amount return self.balance def withdraw(self, amount): """Subtract amount from balance if funds are available.""" if amount > self.balance: return 'Insufficient funds' self.balance = self.balance - amount return self.balance class CheckingAccount(Account): withdraw_fee = 1 def withdraw(self, amount): return Account.withdraw(self, amount + self.withdraw_fee) class Dog(object): """Man's best friend.""" def __init__(self, name): self.name = name self.hunger = 0 def speak(self): self.hunger += 1 return 'woof' def eat(self): self.hunger -= 1 class Collie(Dog): """A heroic breed of dog.""" def speak(self): Dog.speak(self) #return value of 'woof' not used #self.hunger += 1 return 'there is a boy trapped in the well' def eat(self): Dog.eat(self) return 'this food is exquisite' from operator import add def curry(f): def outer(x): def inner(*args): return f(x, *args) return inner return outer class SavingsAccount(Account): """A bank account that charges for deposits.""" deposit_fee = 2 def deposit(self, amount): return Account.deposit(self, amount - self.deposit_fee) def welfare(account): """Deposit $100 into an account if it has less than $100.""" if account.balance < 100: return account.deposit(100) # Special methods and properties from fractions import gcd class Rational(object): """A mutable fraction.""" def __init__(self, numer, denom): g = gcd(numer, denom) self.numerator = numer // g self.denominator = denom // g @property def float_value(self): return self.numerator / self.denominator def __repr__(self): return 'Rational({0}, {1})'.format(self.numerator, self.denominator) def __str__(self): return '{0}/{1}'.format(self.numerator, self.denominator) def __add__(self, num): denom = self.denominator * num.denominator numer1 = self.numerator * num.denominator numer2 = self.denominator * num.numerator return Rational(numer1 + numer2, denom) def __mul__(self, num): return Rational(self.numerator * num.numerator, self.denominator * num.denominator) def __eq__(self, num): return (self.numerator == num.numerator and self.denominator == num.denominator) def __bool__(self): return self.numerator != 0 # Multiple representations from math import atan2, sin, cos, pi def add_complex(z1, z2): """Return a complex number z1 + z2""" return ComplexRI(z1.real + z2.real, z1.imag + z2.imag) def mul_complex(z1, z2): """Return a complex number z1 * z2""" return ComplexMA(z1.magnitude * z2.magnitude, z1.angle + z2.angle) class ComplexRI(object): """A rectangular representation of a complex number. >>> from math import pi >>> add_complex(ComplexRI(1, 2), ComplexMA(2, pi/2)) ComplexRI(1.0000000000000002, 4.0) >>> mul_complex(ComplexRI(0, 1), ComplexRI(0, 1)) ComplexMA(1.0, 3.141592653589793) >>> ComplexRI(1, 2) + ComplexMA(2, 0) ComplexRI(3.0, 2.0) >>> ComplexRI(0, 1) * ComplexRI(0, 1) ComplexMA(1.0, 3.141592653589793) """ def __init__(self, real, imag): self.real = real self.imag = imag @property def magnitude(self): return (self.real ** 2 + self.imag ** 2) ** 0.5 @property def angle(self): return atan2(self.imag, self.real) def __repr__(self): return 'ComplexRI({0}, {1})'.format(self.real, self.imag) def __add__(self, other): return add_complex(self, other) def __mul__(self, other): return mul_complex(self, other) class ComplexMA(object): """A polar representation of a complex number.""" def __init__(self, magnitude, angle): self.magnitude = magnitude self.angle = angle @property def real(self): return self.magnitude * cos(self.angle) @property def imag(self): return self.magnitude * sin(self.angle) def __repr__(self): return 'ComplexMA({0}, {1})'.format(self.magnitude, self.angle) def __add__(self, other): return add_complex(self, other) def __mul__(self, other): return mul_complex(self, other)