You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Commit a4609bb
Browse filesBrowse the repository at this point in the historyBrowse files
Narrow foreach body to non-empty under bleedingEdge
Inside a foreach body the iterated expression is provably non-empty, so it
can be narrowed (list to non-empty-list, array to non-empty-array) at body
entry. Before, this happened only when polluteScopeWithAlwaysIterableForeach
was on, so with the flag off (as phpstan-strict-rules sets it) the narrowing
disappeared even though the body is only entered when the iteratee is
non-empty.
The narrowing is gated behind the new bleedingEdge feature toggle
narrowForeachBodyNonEmpty. With it off the body scope is built exactly as
before, so stable behaviour does not change. With it on, the body narrows
regardless of polluteScopeWithAlwaysIterableForeach.
Narrowing the body also feeds the loop-exit scope, which with the flag off
must stay conservative: we must not conclude the loop always iterated. After
the body pass the iterated expression's possibly-empty-ness is restored in
the after-loop scope (keeping any element types the body refined), so the
value variable does not become always-defined after the loop. Only the
non-emptiness the narrowing introduced is stripped; an iteratee already
non-empty before the loop keeps that property. This containment is partial:
definedness that flows through variables the body builds (rather than through
the iterated expression itself) still reaches the after-loop scope, so a few
value variables can become defined where a proof of non-emptiness exists.
Closesphpstan/phpstan#13312
0 commit comments