Files
AILang/examples/fieldtest/floats_3_safe_division.ail
T
Brummel 832375f2ac convention: counter-prefix file naming across docs/specs/, docs/plans/, design/contracts/, design/models/
All 176 files in the four accumulating directories now use a
zero-padded 4-digit counter prefix that reflects creation order
(`NNNN-slug.md`). The counter is assigned per directory in strict
git-log creation order; ties broken alphabetically by original name.
The old `YYYY-MM-DD-` prefix on docs/specs/ and docs/plans/ files is
dropped — the date is recoverable from git log and the counter
carries the ordering.

A file's counter is stable for the life of the file: never reassigned,
never reused, never compacted. Deleted files retire their counter;
subsequent files do not fill the gap. This is the property that lets
cross-references stay literal — refs use the full filename including
the counter (`design/contracts/0007-honesty-rule.md`) so they grep
cleanly and resolve directly without a glob step.

313 cross-references updated across .md/.rs/.toml/.c/.json files
(test pins, include_str! paths, design-INDEX entries, baseline notes,
runtime C comments, inter-contract markdown links incl. bare basename
and `../models/foo.md` forms).

CLAUDE.md gets a new "File-naming convention" section spelling out
the rule and rationale. skills/brainstorm/SKILL.md and
skills/planner/SKILL.md updated so new spec/plan creation produces
counter-prefixed names from the start.

The full test suite (cargo test --workspace) passes.
2026-05-28 13:31:31 +02:00

56 lines
1.9 KiB
Plaintext

; Fieldtest — Floats milestone, axis 3: NaN / Inf / is_nan handling.
;
; safe_div(a, b) returns a/b when b != 0; falls through to the IEEE
; result otherwise. The fixture exercises four cases:
; 1) 6.0 / 3.0 -> 2.0 (normal)
; 2) 1.0 / 0.0 -> +inf (use is_nan to confirm finite-vs-NaN)
; 3) 0.0 / 0.0 -> NaN (is_nan should report true)
; 4) (- 1.0 1.0) / 0.0 -> NaN (subexpr drives same)
;
; classify(x) returns:
; -1 if x is NaN
; 0 if x is +inf or -inf (we test via x > <huge> / x < -<huge>)
; 1 otherwise
;
; The subtle point: the IEEE-correct way to test for NaN is `is_nan`,
; NOT `(== x x)` (which is false for NaN — but the LLM author who
; reaches for `==` first will get the right answer by accident here,
; only because the natural reading of the operator doesn't apply).
; design/contracts/0005-float-semantics.md says explicitly to use `is_nan`.
;
; Expected stdout (one per line):
; 2.0 ; 6/3
; 1 ; classify(2.0) -> normal
; inf ; 1/0
; 0 ; classify(1/0) -> infinite
; nan ; 0/0
; -1 ; classify(0/0) -> NaN
;
; (`print` for Float routes through `float_to_str`, which uses "%g", so inf prints as "inf", NaN as "nan".)
(module floats_3_safe_division
(fn classify
(doc "-1=NaN, 0=infinite, 1=finite. Uses is_nan + abs > huge.")
(type (fn-type (params (con Float)) (ret (con Int))))
(params x)
(body
(if (app is_nan x)
-1
(if (app float_gt x 1.0e308)
0
(if (app float_lt x -1.0e308)
0
1)))))
(fn main
(type (fn-type (params) (ret (con Unit)) (effects IO)))
(params)
(body
(seq (app print (app / 6.0 3.0))
(seq (app print (app classify (app / 6.0 3.0)))
(seq (app print (app / 1.0 0.0))
(seq (app print (app classify (app / 1.0 0.0)))
(seq (app print (app / 0.0 0.0))
(app print (app classify (app / 0.0 0.0)))))))))))