def number.go

gralha-text-scan@0.1.0.1 · scan.bend:184

import gralha-text-scan@0.1.0.1/scan.bend as Scan
import Base

184# `c` is the character before `t`; `ok` says whether it was read, and the
185# parts are the ones after it. The next character is read when the stage
186# accepts it, and otherwise the parts are kept and the number stops there.
187def number.go(t: String, ok: Bool, +c: U32, mark: String, +stage: U32, +sign: F32, +mant: F32, +div: F32, +esign: F32, +ev: U32, +digits: Bool, +edigits: Bool) -> Number:
188  match t ok:
189    case t False{}: number.finish(SCon{Chr{c}, t}, mark, stage, sign, mant, div, esign, ev, digits, edigits)
190    case SNil{} True{}: number.finish("", mark, stage, sign, mant, div, esign, ev, digits, edigits)
191    case SCon{Chr{c2}, t2} True{}:
192      +cc = c2
193      +k = number.class(cc)
194      +read = number.accepts(k, stage, digits)
195      +isDigit = read && U32.is_eq(k, 0)
196      +inExp = U32.is_ge(stage, 3)
197      +minus = read && U32.is_eq(k, 3) && U32.is_eq(cc, 45)
198      +stage2 = choose(U32, read, number.stage(k, stage), stage)
199      number.go(t2, read, cc, number.mark(read && U32.is_eq(stage2, 3), cc, mark), stage2,
200        choose(F32, minus && U32.is_eq(stage, 0), F32.neg(1.0), sign),
201        choose(F32, isDigit && Bool.not(inExp), (mant * 10.0 + U32.to_f32((cc - 48 : U32)) : F32), mant),
202        choose(F32, isDigit && U32.is_eq(stage, 2), (div * 10.0 : F32), choose(F32, read && U32.is_eq(k, 1), 1.0, div)),
203        choose(F32, minus && U32.is_eq(stage, 3), F32.neg(1.0), esign),
204        choose(U32, isDigit && inExp, (ev * 10 + cc - 48 : U32), ev),
205        digits || (isDigit && Bool.not(inExp)), edigits || (isDigit && inExp))

Uses (24)

Used by (1)