From 93acfab28c5bf3fe5000930e5f04c1d549724355 Mon Sep 17 00:00:00 2001 From: Horizontal42 <75383519+Horizontal42@users.noreply.github.com> Date: Wed, 12 Aug 2026 20:05:44 +0300 Subject: [PATCH] extract asPercentValue in evalPctOp The percent-or-scalar-as-percent conversion was written out twice verbatim in the same function. --- src/engine/evaluator.ts | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/src/engine/evaluator.ts b/src/engine/evaluator.ts index 848ed72..8a7933d 100644 --- a/src/engine/evaluator.ts +++ b/src/engine/evaluator.ts @@ -243,6 +243,11 @@ function evalBit(op: string, l: Value, r: Value): Value { return qty(new Decimal(out.toString()), null, repr); } +/** l already a percent -> its value; otherwise treat the scalar as a whole-number percent. */ +function asPercentValue(l: Value): Decimal { + return l.kind === "percent" ? l.value : asScalar(l).mul(100); +} + function evalPctOp(op: string, l: Value, r: Value): Value { const rq = r.kind === "quantity" ? r : null; const rv = r.kind === "percent" ? r.value.div(100) : rq ? rq.value : null; @@ -250,7 +255,7 @@ function evalPctOp(op: string, l: Value, r: Value): Value { const unit = rq?.unit ?? null; if (op === "of" || op === "off" || op === "on") { - const p = l.kind === "percent" ? l.value : asScalar(l).mul(100); + const p = asPercentValue(l); const factor = op === "of" ? p.div(100) : op === "off" ? new Decimal(1).sub(p.div(100)) @@ -269,7 +274,7 @@ function evalPctOp(op: string, l: Value, r: Value): Value { } } // "20% of what is 30" - const p = l.kind === "percent" ? l.value : asScalar(l).mul(100); + const p = asPercentValue(l); switch (op) { case "of_what_is": return qty(rv.div(p.div(100)), unit); case "off_what_is": {