On Mon, Aug 4, 2025 at 9:26 AM Larry Garfield <la...@garfieldtech.com> wrote:
>
> Hi folks.  I recently wrote a blog post on behalf of the PHP Foundation about 
> some work Gina has been doing regarding generics.  It's a follow-up to last 
> year's post on a similar topic.  We are especially looking for feedback from 
> the Internals crew, and voters in particular, on whether or not to proceed.
>
> https://thephp.foundation/blog/2025/08/05/compile-generics/
>
> Wearing my Internals/voter hat, my stance is a very strong "yes please!"
>
> --
>   Larry Garfield
>   la...@garfieldtech.com

I played with a few iterations of Gina's work. My opinion at that time
was that there are too many restrictions to be very useful. Based on
those evaluations, I would not consider it to be "80% of the
benefit.". With that said, maybe Gina has removed some of the
restrictions. Based on the article it , but I'll commit to trying it
out again.

One thing the article says we're missing and that we we definitely
need is unions, or at the very least the union with null. Nullable
types are everywhere, and even in your interfaces it's going to show
up. For instance, if we had interfaces for Set, Map, etc, there are
going to be operations which return nullable values. Sure, exceptions
can be thrown in some cases but not all of them. For instance, if you
are building a caching data structure, throwing an exceptions on a
cache miss would be very bad for performance*. You can separate it
into has + get, but this has two lookups which is not desirable for
performance. You can return a "tuple" like `[found, $value]` where
`$value` may be null, but this loses even more type safety, and isn't
a very common pattern in PHP. You really want `T|null`.

There are probably other "edges" that are important and should be
handled in this first pass, but missing nullable types is not a small
thing.

* We'll get a mini-optimization in PHP 8.5 for making the exception
object faster to construct, but it doesn't speed up the backtrace,
which is where most of the performance cost comes from in practice. If
you are benchmarking this, make sure to include cases where your stack
is a few dozen frames deep. I work for an observability company for my
day job, and it is insanely normal for there to be 10+ frames, and
still fairly common to be 30+ frames. Think about routing, frameworks,
middleware, helper functions, libraries and abstractions, etc. If you
use middleware in particular, expect 50+ frames to be normal.

Reply via email to