Skip to content

Commit bb03a6f

Browse files
committed
Reuse the digit count condition
1 parent f2a6c79 commit bb03a6f

File tree

1 file changed

+17
-12
lines changed

1 file changed

+17
-12
lines changed

zmij.cc

Lines changed: 17 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -484,9 +484,10 @@ auto to_bcd8(uint64_t abcdefgh) noexcept -> uint64_t {
484484
return is_big_endian() ? a_b_c_d_e_f_g_h : bswap64(a_b_c_d_e_f_g_h);
485485
}
486486

487-
inline auto write_if_nonzero(char* buffer, uint32_t digit) noexcept -> char* {
487+
inline auto write_if(char* buffer, uint32_t digit, bool condition) noexcept
488+
-> char* {
488489
*buffer = char('0' + digit);
489-
return buffer + (digit != 0);
490+
return buffer + condition;
490491
}
491492

492493
inline void write8(char* buffer, uint64_t value) noexcept {
@@ -495,7 +496,8 @@ inline void write8(char* buffer, uint64_t value) noexcept {
495496

496497
// Writes a significand consisting of up to 17 decimal digits (16-17 for
497498
// normals) and removes trailing zeros.
498-
auto write_significand17(char* buffer, uint64_t value) noexcept -> char* {
499+
auto write_significand17(char* buffer, uint64_t value,
500+
bool has17digits) noexcept -> char* {
499501
#if ZMIJ_USE_NEON
500502
// An optimized version for NEON by Dougall Johnson.
501503
constexpr int32_t neg10k = -10000 + 0x10000;
@@ -528,7 +530,7 @@ auto write_significand17(char* buffer, uint64_t value) noexcept -> char* {
528530
uint64_t bbccddee = abbccddee - a * hundred_million;
529531

530532
char* start = buffer;
531-
buffer = write_if_nonzero(buffer, a);
533+
buffer = write_if(buffer, a, has17digits);
532534

533535
uint64x1_t ffgghhii_bbccddee_64 = {(uint64_t(ffgghhii) << 32) | bbccddee};
534536
int32x2_t bbccddee_ffgghhii = vreinterpret_s32_u64(ffgghhii_bbccddee_64);
@@ -570,7 +572,7 @@ auto write_significand17(char* buffer, uint64_t value) noexcept -> char* {
570572
uint32_t a = abbccddee / 100'000'000;
571573
uint32_t bbccddee = abbccddee % 100'000'000;
572574

573-
buffer = write_if_nonzero(buffer, a);
575+
buffer = write_if(buffer, a, has17digits);
574576

575577
alignas(64) static const struct {
576578
__m128i div10k = _mm_set1_epi64x(div10k_sig);
@@ -630,7 +632,7 @@ auto write_significand17(char* buffer, uint64_t value) noexcept -> char* {
630632
// Each digit is denoted by a letter so value is abbccddeeffgghhii.
631633
uint32_t abbccddee = uint32_t(value / 100'000'000);
632634
uint32_t ffgghhii = uint32_t(value % 100'000'000);
633-
buffer = write_if_nonzero(buffer, abbccddee / 100'000'000);
635+
buffer = write_if(buffer, abbccddee / 100'000'000, has17digits);
634636
uint64_t bcd = to_bcd8(abbccddee % 100'000'000);
635637
write8(buffer, bcd | zeros);
636638
if (ffgghhii == 0) {
@@ -645,9 +647,10 @@ auto write_significand17(char* buffer, uint64_t value) noexcept -> char* {
645647

646648
// Writes a significand consisting of up to 9 decimal digits (7-9 for normals)
647649
// and removes trailing zeros.
648-
auto write_significand9(char* buffer, uint32_t value) noexcept -> char* {
650+
auto write_significand9(char* buffer, uint32_t value, bool has9digits) noexcept
651+
-> char* {
649652
char* start = buffer;
650-
buffer = write_if_nonzero(buffer, value / 100'000'000);
653+
buffer = write_if(buffer, value / 100'000'000, has9digits);
651654
uint64_t bcd = to_bcd8(value % 100'000'000);
652655
write8(buffer, bcd | zeros);
653656
buffer += count_trailing_nonzeros(bcd);
@@ -857,15 +860,17 @@ auto write(Float value, char* buffer) noexcept -> char* {
857860
// Write significand.
858861
char* start = buffer;
859862
if (traits::num_bits == 64) {
860-
dec_exp += traits::max_digits10 + (dec.sig >= uint64_t(1e16)) - 2;
861-
buffer = write_significand17(buffer + 1, dec.sig);
863+
bool has17digits = dec.sig >= uint64_t(1e16);
864+
dec_exp += traits::max_digits10 - 2 + has17digits;
865+
buffer = write_significand17(buffer + 1, dec.sig, has17digits);
862866
} else {
863867
if (dec.sig < uint32_t(1e7)) [[ZMIJ_UNLIKELY]] {
864868
dec.sig *= 10;
865869
--dec_exp;
866870
}
867-
dec_exp += traits::max_digits10 + (dec.sig >= uint32_t(1e8)) - 2;
868-
buffer = write_significand9(buffer + 1, dec.sig);
871+
bool has9digits = dec.sig >= uint32_t(1e8);
872+
dec_exp += traits::max_digits10 - 2 + has9digits;
873+
buffer = write_significand9(buffer + 1, dec.sig, has9digits);
869874
}
870875
start[0] = start[1];
871876
start[1] = '.';

0 commit comments

Comments
 (0)