Fix #3386 - fixed.to_string

This commit is contained in:
gingerBill
2024-04-10 14:35:14 +01:00
parent 3ad95d6be3
commit 3b5e515a22
+168 -20
View File
@@ -102,37 +102,51 @@ round :: proc(x: $T/Fixed($Backing, $Fraction_Width)) -> Backing {
return (x.i + (1 << (Fraction_Width - 1))) >> Fraction_Width
}
@(require_results)
append :: proc(dst: []byte, x: $T/Fixed($Backing, $Fraction_Width)) -> string {
Integer_Width :: 8*size_of(Backing) - Fraction_Width
x := x
buf: [48]byte
i := 0
if x.i < 0 {
if !intrinsics.type_is_unsigned(Backing) && x.i == min(Backing) {
// edge case handling for signed numbers
buf[i] = '-'
i += 1
x.i = -x.i
}
integer := x.i >> Fraction_Width
fraction := x.i & (1<<Fraction_Width - 1)
s := strconv.append_uint(buf[i:], u64(integer), 10)
i += len(s)
if fraction != 0 {
buf[i] = '.'
i += 1
for fraction > 0 {
fraction *= 10
buf[i] = byte('0' + (fraction>>Fraction_Width))
i += copy(buf[i:], _power_of_two_table[Integer_Width])
} else {
if x.i < 0 {
buf[i] = '-'
i += 1
fraction &= 1<<Fraction_Width - 1
x.i = -x.i
}
when size_of(Backing) < 16 {
T :: u64
append_uint :: strconv.append_uint
} else {
T :: u128
append_uint :: strconv.append_u128
}
integer := T(x.i) >> Fraction_Width
fraction := T(x.i) & (1<<Fraction_Width - 1)
s := append_uint(buf[i:], integer, 10)
i += len(s)
if fraction != 0 {
buf[i] = '.'
i += 1
for fraction > 0 {
fraction *= 10
buf[i] = byte('0' + (fraction>>Fraction_Width) % 10)
i += 1
fraction &= 1<<Fraction_Width - 1
}
}
}
n := copy(dst, buf[:i])
return string(dst[:i])
}
@@ -146,3 +160,137 @@ to_string :: proc(x: $T/Fixed($Backing, $Fraction_Width), allocator := context.a
copy(str, s)
return string(str)
}
@(private)
_power_of_two_table := [129]string{
"0.5",
"1",
"2",
"4",
"8",
"16",
"32",
"64",
"128",
"256",
"512",
"1024",
"2048",
"4096",
"8192",
"16384",
"32768",
"65536",
"131072",
"262144",
"524288",
"1048576",
"2097152",
"4194304",
"8388608",
"16777216",
"33554432",
"67108864",
"134217728",
"268435456",
"536870912",
"1073741824",
"2147483648",
"4294967296",
"8589934592",
"17179869184",
"34359738368",
"68719476736",
"137438953472",
"274877906944",
"549755813888",
"1099511627776",
"2199023255552",
"4398046511104",
"8796093022208",
"17592186044416",
"35184372088832",
"70368744177664",
"140737488355328",
"281474976710656",
"562949953421312",
"1125899906842624",
"2251799813685248",
"4503599627370496",
"9007199254740992",
"18014398509481984",
"36028797018963968",
"72057594037927936",
"144115188075855872",
"288230376151711744",
"576460752303423488",
"1152921504606846976",
"2305843009213693952",
"4611686018427387904",
"9223372036854775808",
"18446744073709551616",
"36893488147419103232",
"73786976294838206464",
"147573952589676412928",
"295147905179352825856",
"590295810358705651712",
"1180591620717411303424",
"2361183241434822606848",
"4722366482869645213696",
"9444732965739290427392",
"18889465931478580854784",
"37778931862957161709568",
"75557863725914323419136",
"151115727451828646838272",
"302231454903657293676544",
"604462909807314587353088",
"1208925819614629174706176",
"2417851639229258349412352",
"4835703278458516698824704",
"9671406556917033397649408",
"19342813113834066795298816",
"38685626227668133590597632",
"77371252455336267181195264",
"154742504910672534362390528",
"309485009821345068724781056",
"618970019642690137449562112",
"1237940039285380274899124224",
"2475880078570760549798248448",
"4951760157141521099596496896",
"9903520314283042199192993792",
"19807040628566084398385987584",
"39614081257132168796771975168",
"79228162514264337593543950336",
"158456325028528675187087900672",
"316912650057057350374175801344",
"633825300114114700748351602688",
"1267650600228229401496703205376",
"2535301200456458802993406410752",
"5070602400912917605986812821504",
"10141204801825835211973625643008",
"20282409603651670423947251286016",
"40564819207303340847894502572032",
"81129638414606681695789005144064",
"162259276829213363391578010288128",
"324518553658426726783156020576256",
"649037107316853453566312041152512",
"1298074214633706907132624082305024",
"2596148429267413814265248164610048",
"5192296858534827628530496329220096",
"10384593717069655257060992658440192",
"20769187434139310514121985316880384",
"41538374868278621028243970633760768",
"83076749736557242056487941267521536",
"166153499473114484112975882535043072",
"332306998946228968225951765070086144",
"664613997892457936451903530140172288",
"1329227995784915872903807060280344576",
"2658455991569831745807614120560689152",
"5316911983139663491615228241121378304",
"10633823966279326983230456482242756608",
"21267647932558653966460912964485513216",
"42535295865117307932921825928971026432",
"85070591730234615865843651857942052864",
"170141183460469231731687303715884105728",
}