Seldom Seen Smith's Nightmare: \(e^x\)
I recently read "The Monkey Wrench Gang" by Edward Abbey (a 1975 novel about environmental activism and industrial sabotage), and there's a scene where a character known as Seldom Seen Smith has a nightmare. While trying to break into a dam's control room a robot captures him, describes the assembly programming interface for a simple computer, and threatens to electrocute him unless he can implement \(e^x\) as an infinite series within 0.000015ms.
It took me more than 0.000015ms to simulate that machine in Python and write the program, but it was a fun diversion.
#!/bin/env python3 # Evaluate exp(x) with an infinite series, as requested by the # Operator in Seldom Seen Smith's nightmare in The Monkey Wrench Gang # by Edward Abbey. The Operator describes the assembly language for a # simple computer which is simulated here. It took me more than # 0.000015 milliseconds to write this. import math x = 1.0 # Input argument expected_result = math.exp(x) print(f"Input: {x}") print(f"Expecting: {expected_result}") w = x # Working register s = [0.0] * 6 # Storage locations s[0] = 2.0 # Iteration counter s[1] = 1.0 # Factorial s[2] = 1.0 # Partial sum s[3] = x # Powers of x s[4] = 1.0 # Unity (constant) s[5] = x # Input argument (constant) # Functions to simulate the machine's op-codes. def T(n): # Store working register. global w, s s[n] = w def B(n): # Load working register. global w, s w = s[n] def add(n): global w, s w = w + s[n] def sub(n): global w, s w = w - s[n] def mul(n): global w, s w = w * s[n] def div(n): global w, s w = w / s[n] def Z(): exit(0) # End program. print(w, s) add(4) # Add 1 to x. T(2) # Save the result. B(1) # Load factorial. mul(0) # Multiply by iteration count. T(1) # Save result. B(3) # Load power of x. mul(5) # Multiply by x. T(3) # Save result. div(1) # Divide by factorial. add(2) # Add to partial sum. T(2) # Save result. print(w, s) for i in range(0,15): B(0) # Increment iteration counter. add(4) T(0) B(1) # Update factorial. mul(0) T(1) B(3) # Update power of x (x^n). mul(5) T(3) div(1) # Divide by factorial. add(2) # Add to partial sum. T(2) # Save result. print(w, expected_result, w - expected_result, s) Z()
This is a pretty straightforward implementation of this expression for \(e^x\) (copied from Wikipedia):
\[e^x = \sum_{n=0}^\infty {x^n \over n!} = 1 + x + \frac{x^2}{2!} + \frac{x^3}{3!} + \frac{x^4}{4!} + \cdots\]
Jack Crenshaw's book Math Toolkit for Real-Time Programming has a lot to say about improved methods for calculating exponents and other functions. I recommend it.