Skip to main content

Module float_text

Module float_text 

Source
Expand description

Float text, byte-identical to Rust’s formatting and faster.

A tile encodes an f64 hole as format!("{f:?}") when the hole has no format and as format!("{f:.N}") under a .N precision (SRD 114 §7.2). Those bytes are the tile’s contract on every engine, so a faster writer is only admissible if it produces the same bytes for every value. This module is that writer, and tests/float_text.rs is the proof: a differential over edge values, arithmetic series, and a million seeded bit patterns, for the shortest form and every precision 0 through 9.

Shortest form (write_shortest). Rust’s Debug for f64 prints the shortest round-trip digits, as a decimal with at least one fractional digit (100.0, 0.1, -0.0) when the magnitude is in [1e-4, 1e16) and otherwise in exponent form (1e16, 1.5e-7). The ryu crate produces the same shortest digits and, for every class but one, the same layout; the exception is [1e-5, 1e-4), which ryu lays out as 0.00005 and Rust as 5e-5. The writer takes ryu’s text and re-lays out that one class from ryu’s digits. The digits themselves agree except on a tie: a value whose exact decimal expansion is one digit longer than its shortest form and ends in 5 (2231889947293916.25, whose shortest forms …916.2 and …916.3 both round-trip), where ryu rounds to the even digit and Rust rounds up. The writer detects a tie exactly from the float’s odd mantissa and exponent and falls back to format! for it, so the proof’s random sweep is what establishes that no other class differs.

Fixed precision (write_fixed). format!("{f:.N}") rounds the exact binary value to N fractional digits, half to even on the exact decimal expansion. Rounding the shortest digits is not the same operation (0.295 is below the tie in binary, so .2 gives 0.29, where rounding the text 0.295 half-even gives 0.30). The writer decodes the float to m * 2^e and computes round(m * 10^N * 2^e) in u128 arithmetic: for e < 0 the quotient and remainder of a shift, compared against the half; for e >= 0 a left shift with no rounding at all. That is exact wherever m * 10^N * 2^max(e,0) fits in 128 bits, which covers N <= 22 and magnitudes below about 2^(75 - 3.33 N) (1.6e29 at N = 9); every other case falls back to format!, so the output is Rust’s own where the fast path does not reach. A magnitude below the fast path’s shift range is exactly zero at any supported precision and is written as such without a fallback.

Functions§

fixed_is_fast
Whether write_fixed takes the exact fast path for f at prec, or falls back to format!. Exposed so the proof can report its fallback rate.
fixed_string
write_fixed into a new String.
shortest_is_fast
Whether write_shortest takes the ryu path for f, or falls back to format! on a tie. Exposed so the proof can report its fallback rate.
shortest_string
write_shortest into a new String.
write_fixed
Write f exactly as format!("{f:.prec$}") does.
write_shortest
Write f exactly as format!("{f:?}") does.