Calculators and Jupyter

A few days ago, I noticed an error in this Scientific American article (that’s an Apple News link). It led me to thinking about how I use Jupyter Console as a calculator on my Mac.

The article is about Apéry’s constant, which is a particular value of the zeta function: ζ(3). At a conference in 1978, Roger Apéry presented a proof that ζ(3) is irrational. Here’s part of SciAm’s description of his talk:

[Apéry] wrote down an equation that nobody in the room knew but which formed the core of his proof… But someone in attendance had an electronic calculator—an uncommon device at that time—and, with a short program, checked Apéry’s equation and found it correct.

Now, I know essentially nothing about the zeta function or why the irrationality of ζ(3) would be important. But I know a bit about calculators, and the part about calculators being uncommon in 1978 made my eyebrows shoot up.

Famously, the first scientific pocket calculator, the HP-35 from Hewlett-Packard, came out in 1972, six years before this conference. And one of the amazing things about electronic calculators was how quickly they pushed aside slide rules, the calculating devices that had been synonymous with scientists and engineers for decades. They weren’t uncommon; they were everywhere.

OK, you say, but the article mentions “a short program.” Maybe programmable calculators were still uncommon in 1978. Nope. I graduated from high school in 1977 and the gift from my parents was a Texas Instruments SR-52, a programmable calculator that was by then two years old. The notion that a recent graduate of East Aurora High School (Go Tomcats!) would have an ahead-of-its-time electronic device is ludicrous. When I started college in the fall, all my classmates had calculators, and lots of them were programmable.

TI SR-52 from Datamath Calculator Museum

The programmable TI SR-52 (photo from the Datamath Calculator Museum).

The main problem with the SR-52 was that it was awfully big. Later on, when I was in grad school, it proved to be less than robust. Its card reader stopped working and its keys didn’t feel right anymore. So I upgraded to an HP 15C, a much smaller calculator that was seemingly indestructible in the way all HPs in those days were. My 15C was still working great until it was “borrowed” from my office in the mid-90s. I’ve had a couple of calculators since then, and they had wonderful features, but none of them felt as good as the 15C.

(I know HP has resurrected the 15C a couple of times, but I’m not interested. The time of dedicated calculators has passed, and besides, I want my 15C.)

Nowadays, when I’m not at my computer, I use PCalc on my phone. I have it set to RPN mode, and I’ve made both a custom key layout and a handful of special functions that help with the kinds of calculations I tend to do. I can’t imagine using a dedicated calculator again.

But I also can’t imagine using PCalc on my Mac (sorry, James). The calculator interface that feels perfect on my phone has never felt right on a computer screen. Even back in the early days of the Mac, I never used the Calculator desk accessory.

For many years, my desktop calculator of choice has been Jupyter Console running an interactive Python session in the Terminal app.1 Because I know Python’s syntax pretty well, and because Python has a huge library of numerical and scientific functions, I can use Jupyter to quickly solve pretty much any problem that’s within my ability to understand.

I use Jupyter Console rather than Jupyter Notebook or JupyterLab because it starts up quickly and has a Readline interface that I can easily maneuver around in. I seldom need the graphical niceties of a web/notebook interface. I can start it by simply typing jc in the Terminal window because I have this line in my .bashrc file:

alias jc='jupyter console'

I think you can use the same command if your shell is zsh or fish instead of bash.

When starting an interactive Python session, Jupyter Console acts sort of like IPython and reads the file

~/.ipython/profile_default/ipython_config.py

(I have a feeling this is a historical artifact, left over from Jupyter’s early days, and that people starting with Jupyter Console now would put their configuration commands in a different file. But this still works, so I’ve stayed with it.)

In this file, I have these lines:

c.InteractiveShellApp.exec_lines = [
  'from math import *',
  'from trigd import *',
  '%config Completer.use_jedi = False'
]

which are the list of commands to run at the start of a session. The

from math import *

command imports all the math library functions into the main namespace, so I can use common functions like sqrt, log, and the trig and inverse trig functions without needing the math. prefix. Since I’m using Jupyter Console as a calculator, I’ll almost always need these functions, so it saves a step to have them automatically imported.

The last command,

%config Completer.use_jedi = False

has something to do with autocompletion, but I confess I don’t remember why it’s here. Whatever the reason past me had to put it in there, it seems to be working. I’ve never had any trouble with autocompletion.

The most interesting command is the one in the middle,

from trigd import *

There is no trigd in the standard library; it’s a simple library of my own creation that gives me the usual trig and inverse trig functions that work in degrees instead of radians. Here’s the code:

# Trig functions in degrees

from math import sin, cos, tan, asin, acos, atan, atan2, degrees, radians

def sind(x):
    return sin(radians(x))

def cosd(x):
    return cos(radians(x))

def tand(x):
    return tan(radians(x))

def asind(x):
    return degrees(asin(x))

def acosd(x):
    return degrees(acos(x))

def atand(x):
    return degrees(atan(x))

def atan2d(y, x):
    return degrees(atan2(y, x))

While the usual radians-based trig functions are what you need when sine, cosine, etc. arise from the solution of differential equations, degrees-based versions are more useful when the arguments are actual angles (I’ve never seen a protractor or theodolite that reads in radians). I don’t know about you, but I’d much rather type

sind(37)

than

sin(radians(37))

especially in an interactive session. These functions are the equivalent of flipping from radians mode to degrees mode on a scientific calculator.

The names of these functions are stolen from Fortran. I don’t think all dialects of Fortran have “d” versions of the trig functions, but both Intel and GNU Fortran do. Octave, which I used to use as an interactive calculator before switching to Jupyter Console, also has “d” versions of trig functions.

Jupyter Console is also a nice environment for testing out code as it’s being written, but that’s off the calculator topic.


  1. I used iTerm for a while but have returned to Terminal. For the purposes of running Jupyter Console, they’re identical.