Generating equally-spaced floats with least rounding error

Mark Dickinson dickinsm at gmail.com
Sat Sep 24 11:17:49 EDT 2011


On Sep 24, 2:53 pm, Steven D'Aprano <steve
+comp.lang.pyt... at pearwood.info> wrote:
> I'm trying to generate a sequence of equally-spaced numbers between a lower
> and upper limit. Given arbitrary limits, what is the best way to generate a
> list of equally spaced floats with the least rounding error for each point?
>
> For example, suppose I want to divide the range 0 to 2.1 into 7 equal
> intervals, then the end-points of each interval are:
>
> (0.0)---(0.3)---(0.6)---(0.9)---(1.2)---(1.5)---(1.8)---(2.1)
>
> and I'd like to return the values in the brackets. Using Decimal or Fraction
> is not an option, I must use floats. If the exact value isn't representable
> as a float, I'm okay with returning the nearest possible float.

Can you explain why you're constrained not to use Fraction?  Speed?

Using Fraction for intermediate calculations actually works perfectly
for this, since conversions from float to Fraction are exact, while
conversions from Fraction to float are correctly rounded.  So if
you're using Python, you're not too bothered about efficiency, and you
want provably correctly-rounded results, why not use Fraction?

>>> from fractions import Fraction
>>> start, stop, n = 0.0, 2.1, 7
>>> [float(Fraction(start) + i * (Fraction(stop) - Fraction(start)) / n) for i in range(n+1)]
[0.0, 0.3, 0.6, 0.9, 1.2, 1.5, 1.8, 2.1]

--
Mark




More information about the Python-list mailing list