Skip to content

Commit e8fe334

Browse files
authored
math.big: speed up ~10x integer_from_radix() (#24674)
1 parent cecbc72 commit e8fe334

File tree

1 file changed

+21
-7
lines changed

1 file changed

+21
-7
lines changed

vlib/math/big/integer.v

Lines changed: 21 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
module big
22

3+
import math
34
import math.bits
45
import strings
56
import strconv
@@ -272,13 +273,17 @@ fn integer_from_regular_string(characters string, radix u32) Integer {
272273

273274
mut result := zero_int
274275
radix_int := integer_from_u32(radix)
275-
276-
for index := start_index; index < characters.len; index++ {
277-
digit := characters[index]
278-
value := digit_array.index(digit)
279-
280-
result *= radix_int
281-
result += integer_from_int(value)
276+
pow := radix_options[int(radix)]
277+
radix_pow := radix_int.pow(u32(pow))
278+
for i := start_index; i < characters.len; i += pow {
279+
end := math.min(i + pow, characters.len)
280+
num_str := characters[i..end]
281+
if num_str.len == pow {
282+
result *= radix_pow
283+
} else {
284+
result *= radix_int.pow(u32(num_str.len))
285+
}
286+
result += integer_from_u32(regular_string_to_radix(num_str, radix))
282287
}
283288

284289
return Integer{
@@ -287,6 +292,15 @@ fn integer_from_regular_string(characters string, radix u32) Integer {
287292
}
288293
}
289294

295+
fn regular_string_to_radix(characters string, radix u32) u32 {
296+
mut result := u32(0)
297+
298+
for c in characters {
299+
result = result * radix + u32(digit_array.index(c))
300+
}
301+
return result
302+
}
303+
290304
// abs returns the absolute value of the integer `a`.
291305
pub fn (a Integer) abs() Integer {
292306
return if a.signum == 0 {

0 commit comments

Comments
 (0)