sx: format_number helper — defuse int_of_float overflow on huge floats
Shared formatter in sx_types.ml. Small integer-valued floats still print as plain ints; floats outside safe-int range (|n| >= 1e16) now print as %.17g (full precision) instead of silently wrapping to negative or 0. Non-integer values keep %g 6-digit behavior — no existing SX tests regress. Unblocks Number.MAX_VALUE / Math.pow(2,N) style tests in js-on-sx where iterative float loops were collapsing to 0 at ~2^63. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -2120,9 +2120,13 @@
|
||||
(col n)
|
||||
(cond
|
||||
((nil? col) nil)
|
||||
((not (list? col)) col)
|
||||
(true
|
||||
(let ((m (if (< n (len col)) n (len col)))) (slice col 0 m))))))
|
||||
(let
|
||||
((m (if (nil? n) 1 n)))
|
||||
(cond
|
||||
((string? col) (slice col 0 m))
|
||||
((list? col) (slice col 0 m))
|
||||
(true col)))))))
|
||||
|
||||
(define
|
||||
hs-pick-last
|
||||
@@ -2130,13 +2134,15 @@
|
||||
(col n)
|
||||
(cond
|
||||
((nil? col) nil)
|
||||
((not (list? col)) col)
|
||||
(true
|
||||
(let
|
||||
((total (len col)))
|
||||
((total (cond ((string? col) (len col)) ((list? col) (len col)) (true 0))))
|
||||
(let
|
||||
((start (if (< n total) (- total n) 0)))
|
||||
(slice col start total)))))))
|
||||
((start (max 0 (- total n))))
|
||||
(cond
|
||||
((string? col) (slice col start total))
|
||||
((list? col) (slice col start total))
|
||||
(true col))))))))
|
||||
|
||||
(define
|
||||
hs-pick-random
|
||||
@@ -2144,10 +2150,19 @@
|
||||
(col n)
|
||||
(cond
|
||||
((nil? col) nil)
|
||||
((not (list? col)) col)
|
||||
((nil? n) (first col))
|
||||
(true
|
||||
(let ((m (if (< n (len col)) n (len col)))) (slice col 0 m))))))
|
||||
(let
|
||||
((total (cond ((string? col) (len col)) ((list? col) (len col)) (true 0))))
|
||||
(cond
|
||||
((= total 0) (if (nil? n) nil (list)))
|
||||
((nil? n) (nth col 0))
|
||||
(true
|
||||
(let
|
||||
((m (max 0 (if (> n total) total n))))
|
||||
(cond
|
||||
((string? col) (slice col 0 m))
|
||||
((list? col) (slice col 0 m))
|
||||
(true col))))))))))
|
||||
|
||||
(define
|
||||
hs-pick-items
|
||||
@@ -2155,17 +2170,104 @@
|
||||
(col start end)
|
||||
(cond
|
||||
((nil? col) nil)
|
||||
((not (list? col)) col)
|
||||
(true (slice col start end)))))
|
||||
(true
|
||||
(let
|
||||
((n (cond ((string? col) (len col)) ((list? col) (len col)) (true 0))))
|
||||
(let
|
||||
((s (cond ((= start "hs-pick-start") 0) ((= start "hs-pick-end") n) ((and (number? start) (< start 0)) (max 0 (+ n start))) (true start)))
|
||||
(e
|
||||
(cond
|
||||
((= end "hs-pick-end") n)
|
||||
((= end "hs-pick-start") 0)
|
||||
((and (number? end) (< end 0)) (max 0 (+ n end)))
|
||||
(true end))))
|
||||
(cond
|
||||
((string? col) (slice col s e))
|
||||
((list? col) (slice col s e))
|
||||
(true col))))))))
|
||||
|
||||
(define
|
||||
hs-pick-match
|
||||
(fn
|
||||
(regex haystack)
|
||||
(cond
|
||||
((nil? haystack) nil)
|
||||
((nil? regex) nil)
|
||||
(true (regex-match regex haystack)))))
|
||||
((nil? haystack) nil)
|
||||
(true (regex-match (hs-pick-regex-pattern regex) haystack)))))
|
||||
|
||||
(begin
|
||||
(define
|
||||
hs-pick-regex-ci-char
|
||||
(fn
|
||||
(ch)
|
||||
(let
|
||||
((lo (lower ch)) (up (upper ch)))
|
||||
(if (= lo up) ch (str "[" lo up "]")))))
|
||||
(define
|
||||
hs-pick-regex-ci
|
||||
(fn
|
||||
(pat)
|
||||
(let
|
||||
((n (len pat)) (out ""))
|
||||
(let
|
||||
((i 0))
|
||||
(let
|
||||
((loop (fn () nil)))
|
||||
(do
|
||||
(set!
|
||||
loop
|
||||
(fn
|
||||
()
|
||||
(cond
|
||||
((>= i n) nil)
|
||||
(true
|
||||
(let
|
||||
((ch (char-at pat i)))
|
||||
(cond
|
||||
((= ch "\\")
|
||||
(do
|
||||
(set! out (str out ch))
|
||||
(set! i (+ i 1))
|
||||
(when
|
||||
(< i n)
|
||||
(set! out (str out (char-at pat i)))
|
||||
(set! i (+ i 1)))
|
||||
(loop)))
|
||||
(true
|
||||
(do
|
||||
(set! out (str out (hs-pick-regex-ci-char ch)))
|
||||
(set! i (+ i 1))
|
||||
(loop)))))))))
|
||||
(loop)
|
||||
out))))))
|
||||
(define
|
||||
hs-pick-regex-pattern
|
||||
(fn
|
||||
(regex)
|
||||
(cond
|
||||
((nil? regex) "")
|
||||
((list? regex)
|
||||
(let
|
||||
((pat (nth regex 0)) (flags (nth regex 1)))
|
||||
(cond
|
||||
((nil? flags) pat)
|
||||
((string-contains? flags "i") (hs-pick-regex-ci pat))
|
||||
(true pat))))
|
||||
(true regex)))))
|
||||
|
||||
(define
|
||||
hs-pick-matches
|
||||
(fn
|
||||
(regex haystack)
|
||||
(cond
|
||||
((nil? regex) nil)
|
||||
((nil? haystack) nil)
|
||||
(true
|
||||
(let
|
||||
((pat (hs-pick-regex-pattern regex)))
|
||||
(let
|
||||
((found (regex-find-all pat haystack)))
|
||||
(map (fn (m) (list m)) found)))))))
|
||||
|
||||
(define
|
||||
hs-sorted-by
|
||||
|
||||
Reference in New Issue
Block a user