Files
scriptc/tests/corpus/8422-array-isarray-computed.ts
T
Malte UblandClaude Opus 5.5 86299300f6 Fold Array.isArray over a computed argument after evaluating it
`Array.isArray(v)` is a compile-time constant when `v` has a static type:
an `T[]` or a tuple is an array, every other kind is not. The fold only
accepted a bare variable, a record field or a field read, because only
those could be dropped without losing effects, so `Array.isArray(make())`
and `Array.isArray([1, 2])` reached an SC1090 refusal.

A computed argument now folds the same way after being evaluated for its
effects: the value goes into a sequence whose discarded statement is the
argument. Unions keep answering by their runtime tag, and `unknown`
values keep their real runtime test.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-28 05:38:08 -07:00

29 lines
952 B
TypeScript

// `Array.isArray` over a computed argument: a call, an array literal, an
// object literal. The answer comes from the argument's static type, so the
// argument is evaluated for its effects and its value discarded. A union
// argument keeps answering by its runtime tag, and side effects of the
// argument survive the fold.
function rows(): number[] {
return [1, 2];
}
function label(): string {
return "rows";
}
type Pair = [number, string];
function pair(): Pair {
return [3, "three"];
}
let evals = 0;
function counted(): number[] {
evals++;
return [];
}
console.log(Array.isArray(rows()), Array.isArray([1, 2]), Array.isArray({ a: 1 }));
console.log(Array.isArray(label()), Array.isArray(pair()));
console.log(Array.isArray(counted()), evals);
const maybe: string | string[] = ["a"];
const narrow: string | string[] = "a";
console.log(Array.isArray(maybe), Array.isArray(narrow));
console.log(Array.isArray(rows().map((n) => n * 2)));