A lot of custom logic, we basically do arithmetic on character
arrays, but this comes at with huge performance gains.
Unlike coreutils `seq`, we do this for all positive increments
(because why not), and we do not fall back to slow path if
the last parameter is in scientific notation.
Also, add some tests for empty separator, as that may catch
some corner cases.
GNU `seq` doesn't support such large positive exponents anyway,
and we are limited by i64 range, so increase the exponent value
to make sure we fully overflow that range.
Also, add a test to check that a very, very, small number is
treated as 0 (that's also undefined behaviour, but it does
make sense in a way).
Some of these tests are not completely defined behavior, but
in many cases they make sense (or at least one can find some
consistent logic to it).
However, there are 2 edge cases that are more dubious IMHO.
One of them has been reported on list a while back, and I
just reported another.
Tests for both `seq` and `yes` run a command that never terminates,
and check the beggining of their output in stdout, move the copied
parts of the wrapper function to common/util.
We still need to use slightly different logic to parse exit value
as `seq` returns success if stdout gets closed, while `yes` fails.
* seq:enable parsing of hexadecimal floats
Turn on the float parser. Now it's possible to use hexadecimal floats as
parameters. For example,
cargo run -- 0x1p-1 3
0.5
1.5
2.5
Issue #6935
---------
Co-authored-by: Daniel Hofstetter <daniel.hofstetter@42dh.com>
Co-authored-by: Sylvestre Ledru <sylvestre@debian.org>
Improve the error message produced by `seq` when given invalid format
specifiers for the `-f` option. Before this commit:
$ seq -f "%" 1
seq: %: invalid conversion specification
$ seq -f "%g%" 1
seq: %: invalid conversion specification
After this commit:
$ seq -f "%" 1
seq: format '%' ends in %
$ seq -f "%g%" 1
seq: format '%g%' has too many % directives
This matches the behavior of GNU `seq`.
* fix(seq): handle 0e... scientific notation without padding
- Updated the parse_exponent_no_decimal function to treat 0e... as zero.
- Added test cases to verify correct behavior for 0e15 and -w 0e15.
Fix: #6926
* fix(seq): improved parse for accurate BigDecimal handling
* apply missing cargo fmt formatting adjustments
* seq: add the unit test even if they are failing for now
* improve test
Co-authored-by: Daniel Hofstetter <daniel.hofstetter@42dh.com>
---------
Co-authored-by: Daniel Hofstetter <daniel.hofstetter@42dh.com>
* seq: adjust some error messages. GNU's are better
tested by tests/seq/seq.pl
* uucore: remove todo
---------
Co-authored-by: Daniel Hofstetter <daniel.hofstetter@42dh.com>
`seq --format %.2g 10 10` would display `1` because the precision would
not allow room for the decimal point, and the `0` in `10` would be
trimmed as an insignificant trailing `0`.
This has been fixed by only trimming trailing `0` in the presence of a
decimal point.
Change a word in the error message displayed when an increment value
of 0 is provided to `seq`. This commit changes the message from "Zero
increment argument" to "Zero increment value" to match the GNU `seq`
error message.
Add support for the `-f FORMAT` option to `seq`. This option instructs
the program to render each value in the generated sequence using a
given `printf`-style floating point format. For example,
$ seq -f %.2f 0.0 0.1 0.5
0.00
0.10
0.20
0.30
0.40
0.50
Fixes issue #2616.
Fix a bug in which a negative decimal input would not be displayed with
the correct width in the output. Before this commit, the output was
incorrectly
$ seq -w -.1 .1 .11
-0.1
0.0
0.1
After this commit, the output is correctly
$ seq -w -.1 .1 .11
-0.1
00.0
00.1
The code was failing to take into account that the input decimal "-.1"
needs to be displayed with a leading zero, like "-0.1".
Pad infinity and negative infinity values with spaces when using the
`-w` option to `seq`. This corrects the behavior of `seq` to match that
of the GNU version:
$ seq -w 1.000 inf inf | head -n 4
1.000
inf
inf
inf
Previously, it incorrectly padded with 0s instead of spaces.
* seq: use BigDecimal to represent floats
Use `BigDecimal` to represent arbitrary precision floats in order to
prevent numerical precision issues when iterating over a sequence of
numbers. This commit makes several changes at once to accomplish this
goal.
First, it creates a new struct, `PreciseNumber`, that is responsible for
storing not only the number itself but also the number of digits (both
integer and decimal) needed to display it. This information is collected
at the time of parsing the number, which lives in the new
`numberparse.rs` module.
Second, it uses the `BigDecimal` struct to store arbitrary precision
floating point numbers instead of the previous `f64` primitive
type. This protects against issues of numerical precision when
repeatedly accumulating a very small increment.
Third, since neither the `BigDecimal` nor `BigInt` types have a
representation of infinity, minus infinity, minus zero, or NaN, we add
the `ExtendedBigDecimal` and `ExtendedBigInt` enumerations which extend
the basic types with these concepts.
* fixup! seq: use BigDecimal to represent floats
* fixup! seq: use BigDecimal to represent floats
* fixup! seq: use BigDecimal to represent floats
* fixup! seq: use BigDecimal to represent floats
* fixup! seq: use BigDecimal to represent floats