diff --git a/CHANGELOG.md b/CHANGELOG.md index 919159e..8a41f3e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -102,6 +102,14 @@ All notable changes to EigenScript are documented here. max-subtraction (overflow to inf), a mis-indexed target, and sign errors. ### Changed +- **`+` on two lists now names the fix (#680).** `[1,2] + [3,4]` reported + `cannot apply '+' to list and list` — correct but not actionable; a Python/JS + prior lands here and has to guess the idiom. The message now prescribes it: + `... (use 'append of [xs, v]' to add an element, or 'concat of [a, b]' to join + two lists)`, mirroring the existing f-string hint for mixed-type concatenation. + First of the prescriptive-error pass (#680) — errors at points where the + language diverges from mainstream priors should teach the fix, for humans and + AI alike. Regression: `test_error_extra.eigs` EE20b. - **The observer learning-rate gate is now two-channel (entropy *and* drift).** `observer_matrix_scale` throttled a weight matrix to 0.5x whenever its entropy was quiet — but entropy is computed over one SGD step's worth of diff --git a/CLAUDE.md b/CLAUDE.md index 113f2a0..13abd76 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -18,6 +18,16 @@ session: a gap you route upstream is a contribution; a gap you paper over is lost data. Do this without being told, the way you'd run the tests without being told. +## Before merging your own PR, clear ready contributor PRs first + +External contributors work from **forks we cannot push to** — a fork branch is +theirs. If our merge makes their PR stale, the only remedies are asking them to +rebase (friction, delay) or the fetch-rebase-reland dance (see #657). Our OWN PRs +we rebase for free. So before merging one of ours: `gh pr list` and land any +**ready** contributor PR (green + reviewed, not authored by us) first, then rebase +ours onto the new main. Rebasing our own costs nothing; asking them does. (Only +*ready* PRs — never merge an unready contributor PR just to dodge a rebase.) + ## Build & test ``` diff --git a/src/vm.c b/src/vm.c index ac30ebe..daba1b8 100644 --- a/src/vm.c +++ b/src/vm.c @@ -2481,6 +2481,12 @@ static Value *vm_run_ex(EigsChunk *chunk, Env *env, Task *resume) { rt_error(EK_TYPE, current_line, "cannot apply '+' to %s and %s (use an f-string or 'str of' to concatenate)", ta, tb); + else if (a->type == VAL_LIST || b->type == VAL_LIST) + /* #680: name the fix, don't just diagnose. '+' never joins lists + * (it is numbers-or-strings only); a Python/JS prior lands here. */ + rt_error(EK_TYPE, current_line, + "cannot apply '+' to %s and %s (use 'append of [xs, v]' to add an element, or 'concat of [a, b]' to join two lists)", + ta, tb); else rt_error(EK_TYPE, current_line, "cannot apply '+' to %s and %s", ta, tb); vm_push(make_null()); diff --git a/tests/test_error_extra.eigs b/tests/test_error_extra.eigs index 7943475..3c11e81 100644 --- a/tests/test_error_extra.eigs +++ b/tests/test_error_extra.eigs @@ -227,6 +227,18 @@ catch e: assert of [caught20 == 1, "EE20 caught '+' on dict and num"] assert of [(contains of [msg20.message, "cannot apply '+'"]) == 1, "EE20 message mentions cannot apply '+'"] +# ---- '+' on two lists NAMES THE FIX (#680: prescriptive, not just diagnostic) ---- +caught20b is 0 +msg20b is "" +try: + r is [1, 2] + [3, 4] +catch e: + caught20b is 1 + msg20b is e +assert of [caught20b == 1, "EE20b caught '+' on list and list"] +assert of [(contains of [msg20b.message, "append of"]) == 1, "EE20b list '+' message prescribes append"] +assert of [(contains of [msg20b.message, "concat of"]) == 1, "EE20b list '+' message prescribes concat"] + # ---- '/' on incompatible types ---- caught21 is 0 msg21 is ""