Hi
Am 2026-01-20 23:26, schrieb Rowan Tommins [IMSoP]:
As discussed on the other thread, this part of the discussion turns out
be moot, because exactly the same ambiguity exists in the proposed
syntax:
let($foo = bar($baz), $baz=1) { ... }
The syntax alone doesn't tell you what that will do, only knowing the
choices made in the RFC.
Yes, syntax alone does not give you any guarantees. But it provides an
indication of which possible choice is more likely to be made. That's
also why I tried to emphasize and explain how the different syntax works
with my intuition (e.g. by using “suggests” or “strongly suggests” as
the phrasing). You may disagree of course. Different brains work
differently and different experiences with different programming
languages probably also shape how one reasons about the code.
Other languages have other ecosystems and other user expectations. PHP
has extensive “scope introspection” functionality by means of
`extract()`, `compact()`, `get_defined_vars()` and variable variables.
Folks are used to being able to access arbitrary variables (it's just
a Warning, not an Error to access undefined variables) and there's
also constructs like `isset()` that can act on plain old local-scope
variables. Adding semantics like the “temporal dead zone” from
JavaScript that you suggested in the other thread would mean that we
would need to have entirely new semantics and interactions with
various existing language features that folks already know, adding to
the complexity of the language.
I don't think most of these would need special semantics at all. If
it's an error to read from $foo, it follows that it's an error to read
from $$x when $x is 'foo', and an error to run compact('foo').
I could've probably phrases it more clearly: I don't think the existence
of a temporal dead zone is a good idea for PHP. I find it especially
unexpected to be disallowed to write to a variable (i.e. more extract()
rather than compact()).
For me this works, because the `let()` is preparing me that “this code
is doing user processing” and the `if()` is just an “implementation
detail” / “means to an end” of that. By the block scoping semantics I
know that when I read the closing brace, the user processing is
finished. The function is a <h1>, the user processing is a <h2> and
the `if()` is a <h3> if that analogy makes sense. If I just want to
get an overview over the function, I only care about the <h2>
headings.
I can't think of any situation where "this block of code contains a
scoped variable" is more important information than "this block of code
might not run at all".
Note that the quoted wording said “this code deals with user processing”
not “this block contains a scoped variable”. The variable *name* is
important information there and knowing that this variable name will not
be used after the block is important to me, because then I know that
user processing is finished.
In the analogy, I would always class an if() as an h2; it's one of the
most fundamental pieces of control flow.
How the user is being processed (e.g. conditionally) is then the h3.
I think, in a nutshell, this is where we have opposing opinions:
It looks like that. And IMO it is totally fine. If we always were in
agreement, we wouldn't need RFCs, Discussions and Votes and would just
commit to master :-) As I mentioned in the “Intent to Vote” email, we
nevertheless found this discussion very valuable and are thankful you
took the time to engage.
Best regards
Tim Düsterhus