简体   繁体   中英

Python Scientific Notation precision normalizing

My goal is simply to convert a string such as "1.2" to scientific notation without adding additional precision. The problem is that I always end up with superfluous 0s at the end of my output.

>>> input = "1.2"
>>> print '{:e}'.format(float(input))
1.200000e+00

I'm trying to figure out how to get just 1.2e+00 . I realize I can specify precision in my format statement, but I don't want to truncate longer strings unnecessarily. I just want to suppress the training 0s.

I've tried using Decimal.normalize(), which works in all cases, except where e < 2.

>>> print Decimal("1.2000e+4").normalize()
1.2E+4
>>> print Decimal("1.2000e+1").normalize()
12

So that's better, except I don't want 12, I want 1.2e+1. :P

Any suggestions would be greatly appreciated!

Edit: To clarify, the input value has already been rounded appropriately to a predetermined length that is now unknown. I'm trying to avoid recalculating the appropriate formatting precision.

Basically, I could have input values of "1.23" and "1234.56", which should come out as "1.23e+0" and "1.23456e+3".

I may have to just check how long the input string is and use that to specify a precision manually, but I wanted to check and make sure I just wasn't missing something that could just prevent the exponential format from arbitrarily adding 0s.

You can specify precision in the format:

print '{:.2e}'.format(float(input))

This will always give 2 decimals of precision. The amount of precision you want must be determined by yourself. If you need any help with that post in the comments.

Just going back through and cleaning up old questions. I ended up solving this by writing a little function to intuit the initial precision of a number and then using it to format the output result.

#used to determine number of precise digits in a string
def get_precision(str_value):
    vals =  str_value.split('.')
    if (vals[0] == '0'):
        return len(vals[1])
    else:
        return len(str_value) -1

# maintain same precision of incoming string on output text
class ExpDecorator(CurrencyDecorator):
    def get_text(self):
        text = self.decoratedCurrency.get_text()
        return ('{:.' + str(get_precision(text)-1) + 'e}').format(float(text))

Not really the most elegant solution, but the task was kind of obnoxious to begin with and it got the job done.

It took a bit of tweaking Alex's solution but I wrote a function that would remove all trailing zeros from any number in python.

def remove_trailing_zeros(value):
value = str(value)
if value.find('e') != -1:
    vals = value.split('e')
    e = vals[1]
    return '{:g}'.format(float(vals[0]))+'e'+e
vals = value.split('.')
if (vals[0] == '0'):
    i = 0
    while vals[1][i] == '0':
        i += 1
    return '{:.{}e}'.format(float(value), len(vals[1][i:]) - 1)
else:
    j = len(vals[0]) - 1
    while vals[0][j] == '0':
        j -= 1
    return '{:.{}e}'.format(float(value), len(vals[0][:j]))

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM