2

I want a function that given a measurement and the error estimate, will round the error to a specified number of significant figures, and round the measurement value to the corresponding digit. Here is an example of inputs and expected outputs:

>>> g = 6.6740813489701e-11
>>> g_err = 0.0003133212341e-11
>>> round_sig_figs(g, g_err, sig_figs=2)
(6.67408e-11, 3.1e-15)

Typically errors are reported with 2 significant figures. I want a function that will return a value's error estimate with this level of precision and also truncate the value to the correct decimal place.

glibdud
  • 7,550
  • 4
  • 27
  • 37
Steven C. Howell
  • 16,902
  • 15
  • 72
  • 97
  • Just a suggestion: The current subject line does not adequately capture the thrust of your question. As it stands now, almost anyone reading the subject will immediately think "why doesn't he just use `round()` already?". And their second thought will be "ah, maybe he has issues with the way floating point rounds unintuitively, and so he needs to look at the `decimal` module". Those types of questions have been asked many, many times before on Stack Overflow. You ought to pick a subject line that differentiates your question from those. – John Y Jan 27 '17 at 16:15
  • In particular, you want a subject line that makes it clear you're not simply duplicating [this](http://stackoverflow.com/questions/3410976/how-to-round-a-number-to-significant-figures-in-python?rq=1). Or, if this *is* a duplicate of that, then this one should be closed as such. – John Y Jan 27 '17 at 16:18
  • @JohnY, thank you for pointing out my lack of clarity. Hopefully the updated subject is better. – Steven C. Howell Jan 27 '17 at 18:21

2 Answers2

0

This function accomplishes this task but if there is a more Pythonic method please add another answer.

import numpy as np

def round_sig_figs(val, val_err, sig_figs=2):
    '''
    Round a value and its error estimate to a certain number 
    of significant figures (on the error estimate).  By default 2
    significant figures are used.
    '''

    n = int(np.log10(val_err))  # displacement from ones place
    if val_err >= 1:
        n += 1

    scale = 10 ** (sig_figs - n)
    val = round(val * scale) / scale
    val_err = round(val_err * scale) / scale

    return val, val_err

Here is the listed example:

>>> g = 6.6740813489701e-11
>>> g_err = 0.0003133212341e-11
>>> round_sig_figs(g, g_err)
(6.67408e-11, 3.1e-15)

Here is an example of a value larger than one but rounding in the decimal places:

>>> g_earth = 9.80665
>>> g_earth_err = 0.042749999
>>> round_error(g_earth, g_earth_err)
(9.807, 0.043)

Here is an example of a value much larger than one:

>>> r = 6371293.103132049
>>> r_err = 14493.004419708
>>> round_error(r, r_err)
(6371000.0, 14000.0)
Steven C. Howell
  • 16,902
  • 15
  • 72
  • 97
0

Python has an built-in function to achieve this:

round(num, ndigits)

See: https://docs.python.org/2/library/functions.html#round

Theo Emms
  • 293
  • 1
  • 7
  • This does not give desired output – Wondercricket Jan 27 '17 at 16:05
  • This would only work in some cases, when the digits of interest are after the decimal. `ndigits` is the number of "digits after the decimal point", not the number of significant figures. I updated the subject to make this more clear. – Steven C. Howell Jan 27 '17 at 18:20