""" Simple no bells and whistles rational number class used to help students with "__rib__ syntax" i.e. triggering specially named functions like __add__ using the + operator. Placed in the public domain by: Kirby Urner Saturday Academy Silicon Forest, Oregon Usage: >>> from rationals import Rat >>> somerat = Rat(2,3) >>> otherat = Rat(5,12) >>> somerat + otherat (13/12) >>> somerat * Rat(3,2) (1/1) >>> somerat * otherat (5/18) """ def gcd(a,b): """ Euclid's Algorithm """ while b: a, b = b, a%b return a def lcm(a,b): return (a*b)/gcd(a,b) class Rat: """ Bare bones Rational; feel free to enhance (e.g. __pow__) """ def __init__(self, numer, denom): """reduce to lowest terms at birth""" thegcd = gcd(numer, denom) # gcd a global self.numer = numer/thegcd self.denom = denom/thegcd def __add__(self, other): """add using common denominator""" commondenom = lcm(self.denom, other.denom) # lcm a global newnumera = (commondenom/self.denom)*self.numer newnumerb = (commondenom/other.denom)*other.numer return Rat(newnumera + newnumerb, commondenom) def __neg__(self): return Rat(-self.numer, self.denom) def __sub__(self, other): return self + (-other) def __mul__(self, other): """multiplying is easier...""" return Rat(self.numer * other.numer, self.denom*other.denom) def __div__(self, other): """multiply by reciprocal (= mult. inverse)""" return Rat(self.numer * other.denom, other.numer * self.denom) def __repr__(self): """show me!""" return "(%s/%s)" % (self.numer, self.denom) def testit(): somerat = Rat(2,3) otherat = Rat(5,12) print somerat print otherat print "%s + %s = %s" % (somerat, otherat, somerat + otherat) print "%s - %s = %s" % (somerat, otherat, somerat - otherat) print "%s * %s = %s" % (somerat, otherat, somerat * otherat) print "%s / %s = %s" % (somerat, otherat, somerat / otherat) print "- %s = %s" % (somerat, -somerat) if __name__ == "__main__": testit()