Refactor spire.math.Interval for speed and correctness.

This commit changes the way Spire handles intervals. It removes the
bound objects (whose unop/binop logic was a bit faulty), instead
using interval subtypes and flags. There are four types of intervals:

  1. All: the interval containing all values
  2. Above(lower): the interval above a lower bound
  3. Below(upper): the interval below an upper bound
  4. Ranged(lower, upper): an interval bounded by two values

Each bound may be open or closed using a flag, which are not meant to
be user-visible. There were a lot of issues with unbound intervals
that stemmed from treaing open/closed/unbound with the same logic,
which this design fixes.