# pragma once
// Copyright (c) 2022 James Edward Anhalt III - https://github.com/jeaiii/itoa
using u32 = decltype ( 0xffffffff ) ;
using u64 = decltype ( 0xffffffffffffffff ) ;
static_assert ( u32 ( - 1 ) > 0 , " u32 must be unsigned " ) ;
static_assert ( u32 ( 0xffffffff ) + u32 ( 1 ) = = u32 ( 0 ) , " u32 must be 32 bits " ) ;
static_assert ( u64 ( - 1 ) > 0 , " u64 must be unsigned " ) ;
static_assert ( u64 ( 0xffffffffffffffff ) + u32 ( 1 ) = = u32 ( 0 ) , " u64 must be 64 bits " ) ;
constexpr auto digits_00_99 =
" 00010203040506070809 " " 10111213141516171819 " " 20212223242526272829 " " 30313233343536373839 " " 40414243444546474849 "
" 50515253545556575859 " " 60616263646566676869 " " 70717273747576777879 " " 80818283848586878889 " " 90919293949596979899 " ;
struct pair { char t , o ; } ;
# define JEAIII_W(I, U) *(pair*)&b[I] = *(pair*)&digits_00_99[(U) * 2]
# define JEAIII_A(I, N) t = (u64(1) << (32 + N / 5 * N * 53 / 16)) / u32(1e##N) + 1 + N / 6 - N / 8, t *= u, t >>= N / 5 * N * 53 / 16, t += N / 6 * 4, JEAIII_W(I, t >> 32)
# define JEAIII_S(I) b[I] = char(u64(10) * u32(t) >> 32) + '0'
# define JEAIII_D(I) t = u64(100) * u32(t), JEAIII_W(I, t >> 32)
# define JEAIII_C0(I) b[I] = char(u) + '0'
# define JEAIII_C1(I) JEAIII_W(I, u)
# define JEAIII_C2(I) JEAIII_A(I, 1), JEAIII_S(I + 2)
# define JEAIII_C3(I) JEAIII_A(I, 2), JEAIII_D(I + 2)
# define JEAIII_C4(I) JEAIII_A(I, 3), JEAIII_D(I + 2), JEAIII_S(I + 4)
# define JEAIII_C5(I) JEAIII_A(I, 4), JEAIII_D(I + 2), JEAIII_D(I + 4)
# define JEAIII_C6(I) JEAIII_A(I, 5), JEAIII_D(I + 2), JEAIII_D(I + 4), JEAIII_S(I + 6)
# define JEAIII_C7(I) JEAIII_A(I, 6), JEAIII_D(I + 2), JEAIII_D(I + 4), JEAIII_D(I + 6)
# define JEAIII_C8(I) JEAIII_A(I, 7), JEAIII_D(I + 2), JEAIII_D(I + 4), JEAIII_D(I + 6), JEAIII_S(I + 8)
# define JEAIII_C9(I) JEAIII_A(I, 8), JEAIII_D(I + 2), JEAIII_D(I + 4), JEAIII_D(I + 6), JEAIII_D(I + 8)
# define JEAIII_L(N, A, B) u < u32(1e##N) ? A : B
# define JEAIII_L09(F) JEAIII_L(2, JEAIII_L(1, F(0), F(1)), JEAIII_L(6, JEAIII_L(4, JEAIII_L(3, F(2), F(3)), JEAIII_L(5, F(4), F(5))), JEAIII_L(8, JEAIII_L(7, F(6), F(7)), JEAIII_L(9, F(8), F(9)))))
# define JEAIII_L03(F) JEAIII_L(2, JEAIII_L(1, F(0), F(1)), JEAIII_L(3, F(2), F(3)))
# define JEAIII_K(N) (JEAIII_C##N(0), b + N + 1)
# define JEAIII_KX(N) (JEAIII_C##N(0), u = x, JEAIII_C7(N + 1), b + N + 9)
# define JEAIII_KYX(N) (JEAIII_C##N(0), u = y, JEAIII_C7(N + 1), u = x, JEAIII_C7(N + 9), b + N + 17)
template < bool B , class T , class F > struct _cond { using type = F ; } ;
template < class T , class F > struct _cond < true , T , F > { using type = T ; } ;
template < bool B , class T , class F > using cond = typename _cond < B , T , F > : : type ;
template < class T > inline char * to_text_from_integer ( char * b , T i )
{
u64 t = u64 ( i ) ;
if ( i < T ( 0 ) )
t = u64 ( 0 ) - t , b [ 0 ] = ' - ' , + + b ;
u32 u = cond < T ( 1 ) ! = T ( 2 ) , cond < sizeof ( T ) ! = 1 , cond < sizeof ( T ) ! = sizeof ( short ) , u32 , unsigned short > , unsigned char > , bool > ( t ) ;
// if our input type fits in 32bits, or its value does, ctreat as 32bit (the line above ensures the compiler can still know the range limits of the input type)
// and optimize out cases for small integer types (if only c++ had a builtin way to get the unsigned type from a signed type)
if ( sizeof ( i ) < = sizeof ( u ) | | u = = t )
return JEAIII_L09 ( JEAIII_K ) ;
u32 x = t % 100000000u ;
u = u32 ( t / = 100000000u ) ;
// t / 10^8 (fits in 32 bit), t % 10^8 -> ~17.5 digits
if ( u = = t )
return JEAIII_L09 ( JEAIII_KX ) ;
// t / 10^16 (1-4 digits), t / 10^8 % 10^8, t % 10^8
u32 y = t % 100000000u ;
u = u32 ( t / 100000000u ) ;
return JEAIII_L03 ( JEAIII_KYX ) ;
}
inline char * to_text ( char text [ ] , signed char i ) { return to_text_from_integer ( text , i ) ; }
inline char * to_text ( char text [ ] , unsigned char i ) { return to_text_from_integer ( text , i ) ; }
inline char * to_text ( char text [ ] , short i ) { return to_text_from_integer ( text , i ) ; }
inline char * to_text ( char text [ ] , unsigned short i ) { return to_text_from_integer ( text , i ) ; }
inline char * to_text ( char text [ ] , int i ) { return to_text_from_integer ( text , i ) ; }
inline char * to_text ( char text [ ] , unsigned int i ) { return to_text_from_integer ( text , i ) ; }
inline char * to_text ( char text [ ] , long i ) { return to_text_from_integer ( text , i ) ; }
inline char * to_text ( char text [ ] , unsigned long i ) { return to_text_from_integer ( text , i ) ; }
inline char * to_text ( char text [ ] , long long i ) { return to_text_from_integer ( text , i ) ; }
inline char * to_text ( char text [ ] , unsigned long long i ) { return to_text_from_integer ( text , i ) ; }
// Copyright (c) 2022 Bill Sun
# if defined(__SIZEOF_INT128__)
constexpr static __uint128_t _10_19 = 10000000000000000000ull ,
_10_37 = _10_19 * _10_19 / 10 ;
template < class T >
char * jeaiii_i128 ( char * buf , T v ) {
if constexpr ( std : : is_signed_v < T > ) {
if ( v < 0 ) {
* ( buf + + ) = ' 0 ' ;
v = - v ;
}
}
if ( v > _10_37 ) {
uint8_t vv = uint8_t ( v / _10_37 ) ;
// vv <<= 1;
// if (vv < 20)
// *buf ++ = digits_00_99[vv + 1];
// else{
// memcpy(buf, digits_00_99 + vv, 2);
// buf += 2;
// }
* ( buf + + ) = vv % 10 + ' 0 ' ;
vv / = 10 ;
if ( vv ) {
* buf = * ( buf - 1 ) ;
* ( buf + + - 1 ) = vv + ' 0 ' ;
}
}
if ( v > _10_19 )
buf = to_text ( buf , uint64_t ( ( v / _10_19 ) % _10_19 ) ) ;
buf = to_text ( buf , uint64_t ( v % _10_19 ) ) ;
return buf ;
}
# endif // INT128