On 28/06/2021 21:28, Olle Härstedt wrote:
Sorry for hijacking the thread, but are there no other alternatives,
really? Just brainstorming:

1) Setting to silence the warning.


Just to reiterate: in PHP 8.0, an undefined constant is not a warning, it's an error. My apologies to code golfers: you can no longer save two bytes by leaving the quote marks off your strings.

However, that's not really the problem. The problem is when there *is* a constant with that name:

const foo='strtoupper';
function foo($x) { return 'test'; }
$input = ['hello', 'world'];
var_dump( array_map(foo, $input) ); // this runs strtoupper(), not foo()

This doesn't work even in old versions of PHP where undefined constants fell back to strings.

Even in cases where this trick did work in older versions of PHP, it was just a variant of option one, "use our current ugly callable syntax" - it saved you those two bytes, but it didn't actually provide you a function reference.

Unifying the constant and function name tables would not be to just a different way of writing strings, it would let array_map(foo, $input) actually check that function foo existed, and represent callables as a proper type. Meanwhile, to let array_map($object->foo, $input) do the same thing (instead of the current [$object, 'foo'] syntax) you also need to unify the method and property tables, which is probably even harder.



2) Setting to silence the warning IF and only if argument expects a
callable, like in array_map (won't work with a pipe() function,
though, since pipe() would take any number of arguments and that can't
be typed)


In the general case, this is a non-starter: the parameters need to be parsed from the source code before function definitions are even known. You could special-case a handful of built-in functions, but that would be extremely clunky.



3) Silence the warning if you type-case explicitly, like in
`pipe($start, (callable) htmlentities);`. Another alternative is
`(fn)` as a type-cast. Not much better than `pipe($start,
htmlentities(?))`, I guess. Just different style.


This falls into my third option: "add a dedicated callable syntax". That could be something that looks a bit like PFA but isn't, like Nikita's RFC; or something that looks a bit like a type cast; or any number of other ideas which have been brainstormed for about as long as I've been programming PHP.


4) Silence the warning ONLY when it's the right-hand argument to pipe
operator, like `$start |> str_len`.


Re-wording this as "interpret the unquoted word as a function reference rather than a constant when...", this one is at least plausible. In practice, though, a lot of functions don't take only one parameter, so the previous pipe proposal included a placeholder for which argument you wanted to "pipe into". At which point you don't need to special case keywords, because you can just write this:

$start |> str_len($$)


Regards,

--
Rowan Tommins
[IMSoP]

--
PHP Internals - PHP Runtime Development Mailing List
To unsubscribe, visit: https://www.php.net/unsub.php

Reply via email to