summaryrefslogtreecommitdiff
path: root/py/formatfloat.c
AgeCommit message (Collapse)Author
7 dayspy/formatfloat: Improve accuracy of float formatting code.Yoctopuce dev
Following discussions in PR #16666, this commit updates the float formatting code to improve the `repr` reversibility, i.e. the percentage of valid floating point numbers that do parse back to the same number when formatted by `repr` (in CPython it's 100%). This new code offers a choice of 3 float conversion methods, depending on the desired tradeoff between code size and conversion precision: - BASIC method is the smallest code footprint - APPROX method uses an iterative method to approximate the exact representation, which is a bit slower but but does not have a big impact on code size. It provides `repr` reversibility on >99.8% of the cases in double precision, and on >98.5% in single precision (except with REPR_C, where reversibility is 100% as the last two bits are not taken into account). - EXACT method uses higher-precision floats during conversion, which provides perfect results but has a higher impact on code size. It is faster than APPROX method, and faster than the CPython equivalent implementation. It is however not available on all compilers when using FLOAT_IMPL_DOUBLE. Here is the table comparing the impact of the three conversion methods on code footprint on PYBV10 (using single-precision floats) and reversibility rate for both single-precision and double-precision floats. The table includes current situation as a baseline for the comparison: PYBV10 REPR_C FLOAT DOUBLE current = 364688 12.9% 27.6% 37.9% basic = 364812 85.6% 60.5% 85.7% approx = 365080 100.0% 98.5% 99.8% exact = 366408 100.0% 100.0% 100.0% Signed-off-by: Yoctopuce dev <dev@yoctopuce.com>
2023-10-03all: Fix various spelling mistakes found by codespell 2.2.6.Damien George
Signed-off-by: Damien George <damien@micropython.org>
2023-04-27all: Fix spelling mistakes based on codespell check.Damien George
Signed-off-by: Damien George <damien@micropython.org>
2022-08-12py/formatfloat: Use pow(10, e) instead of pos/neg_pow lookup tables.Dan Ellis
Rework the conversion of floats to decimal strings so it aligns precisely with the conversion of strings to floats in parsenum.c. This is to avoid rendering 1eX as 9.99999eX-1 etc. This is achieved by removing the power- of-10 tables and using pow() to compute the exponent directly, and that's done efficiently by first estimating the power-of-10 exponent from the power-of-2 exponent in the floating-point representation. Code size is reduced by roughly 100 to 200 bytes by this commit. Signed-off-by: Dan Ellis <dan.ellis@gmail.com>
2022-07-26py/formatfloat: Format all whole-number floats exactly.Dan Ellis
Formerly, py/formatfloat would print whole numbers inaccurately with nonzero digits beyond the decimal place. This resulted from its strategy of successive scaling of the argument by 0.1 which cannot be exactly represented in floating point. The change in this commit avoids scaling until the value is smaller than 1, so all whole numbers print with zero fractional part. Fixes issue #4212. Signed-off-by: Dan Ellis dan.ellis@gmail.com
2020-04-18all: Fix implicit conversion from double to float.stijn
These are found when building with -Wfloat-conversion.
2020-02-28all: Reformat C and Python source code with tools/codeformat.py.Damien George
This is run with uncrustify 0.70.1, and black 19.10b0.
2018-03-01py/formatfloat: Fix case where floats could render with negative digits.Damien George
Prior to this patch, some architectures (eg unix x86) could render floats with "negative" digits, like ")". For example, '%.23e' % 1e-80 would come out as "1.0000000000000000/)/(,*0e-80". This patch fixes the known cases.
2018-03-01py/formatfloat: Fix case where floats could render with a ":" character.Damien George
Prior to this patch, some architectures (eg unix x86) could render floats with a ":" character in them, eg 1e+39 would come out as ":e+38" (":" is just after "9" in ASCII so this is like 10e+38). This patch fixes some of these cases.
2018-03-01py/formatfloat: Fix rounding of %f format with edge-case FP values.Damien George
Prior to this patch the %f formatting of some FP values could be off by up to 1, eg '%.0f' % 123 would return "122" (unix x64). Depending on the FP precision (single vs double) certain numbers would format correctly, but others wolud not. This patch should fix all cases of rounding for %f.
2017-10-10py/formatfloat: Use standard isinf, isnan funcs instead of custom ones.Damien George
Reduces code size by a tiny bit.
2017-10-10py/formatfloat: Don't print the negative sign of a NaN value.Damien George
NaN may have the sign bit set but it has no meaning, so don't print it out.
2017-08-21py/formatfloat: Don't post-increment variable that won't be used again.Damien George
2017-07-31all: Use the name MicroPython consistently in commentsAlexander Steffen
There were several different spellings of MicroPython present in comments, when there should be only one.
2017-07-19all: Remove trailing spaces, per coding conventions.Damien George
2017-07-07py,extmod: Some casts and minor refactors to quiet compiler warnings.Tom Collins
2017-06-13py/formatfloat: Fix number of digits and exponent sign when rounding.Damien George
This patch fixes 2 things when printing a floating-point number that requires rounding up of the mantissa: - retain the correct precision; eg 0.99 becomes 1.0, not 1.00 - if the exponent goes from -1 to 0 then render it as +0, not -0
2017-01-19py/formatfloat: Remove unreachable code.Damien George
The if-block that this unreachable code is in has a condition "f>=5" so "fp_isless1(f)" will always fail.
2016-03-29py/formatfloat: Fix further cases of buffer overflow in formatting.Damien George
Includes extensive test cases to catch hopefully all cases where buffer might overflow.
2016-03-29py/formatfloat: Fix case of float format where leading digit was "10".Damien George
When taking the logarithm of the float to determine the exponent, there are some edge cases that finish the log loop too large. Eg for an input value of 1e32-epsilon, this is actually less than 1e32 from the log-loop table and finishes as 10.0e31 when it should be 1.0e32. It is thus rendered as :e32 (: comes after 9 in ascii). There was the same problem with numbers less than 1.
2016-03-15py/formatfloat: Fix buffer overflow when formatting tiny numbers.Damien George
2016-01-29py/formatfloat: Add ability to format doubles with exponents > 99.Damien George
For single prec, exponents never get larger than about 37. For double prec, exponents can be larger than 99 and need 3 bytes to format. This patch makes the number of bytes needed configurable. Addresses issue #1772.
2015-11-22py/formatfloat: Handle calculation of integer digit for %f format properly.Paul Sokolovsky
%f prints true integer digit, so its calculation should happen before any exponential scaling.
2015-11-22py/formatfloat: Workaround (fix?) incorrect rounding for %f format.Paul Sokolovsky
2015-11-22py/formatfloat: Convert to fully portable implementation.Paul Sokolovsky
This takes previous IEEE-754 single precision float implementation, and converts it to fully portable parametrizable implementation using C99 functions like signbit(), isnan(), isinf(). As long as those functions are available (they can be defined in adhoc manner of course), and compiler can perform standard arithmetic and comparison operations on a float type, this implementation will work with any underlying float type (including types whose mantissa is larger than available intergral integer type).
2015-09-11stmhal: fix single precision float printing errorDave Hylands
Fixes #1435.
2015-05-17py: Implement mp_format_float for doubles and use where appropriatestijn
This allows using (almost) the same code for printing floats everywhere, removes the dependency on sprintf and uses just snprintf and applies an msvc-specific fix for snprintf in a single place so nan/inf are now printed correctly.
2015-04-12py/formatfloat.c: Fix format of floating point numbers near 1.0.Dave Hylands
In particular, numbers which are less than 1.0 but which round up to 1.0. This also makes those numbers which round up to 1.0 to print with e+00 rather than e-00 for those formats which print exponents. Addresses issue #1178.
2015-01-01py: Move to guarded includes, everywhere in py/ core.Damien George
Addresses issue #1022.
2014-07-17formatfloat.c: Typo fix in comment.Paul Sokolovsky
2014-05-03Add license header to (almost) all files.Damien George
Blanket wide to all .c and .h files. Some files originating from ST are difficult to deal with (license wise) so it was left out of those. Also merged modpyb.h, modos.h, modstm.h and modtime.h in stmhal/.
2014-04-01Enhance str.format supportDave Hylands
This adds support for almost everything (the comma isn't currently supported). The "unspecified" type with floats also doesn't behave exactly like python. Tested under unix with float and double Spot tested on stmhal
2014-03-17py: Clean up includes.xbe
Remove unnecessary includes. Add includes that improve portability.
2014-03-10Rename formatfloat file; remove MICROPY_ENABLE_FLOAT from mpconfigport.h.Damien George
MICROPY_ENABLE_FLOAT is automatically set in mpconfig.h if MICROPY_FLOAT_IMPL is set to a non-zero value.