Re: Feature Discussion |

From: Date: Wed, 11 Jun 2025 06:56:44 +0000
Subject: Re: Feature Discussion |
References: 1 2 3 4 5  Groups: php.internals 
Request: Send a blank email to internals+get-127642@lists.php.net to get a copy of this message
On Wed, Jun 11, 2025, at 08:31, Dmitry Derepko wrote: > I see. > > The first thought is about extending the class definition: along with functions hashtable we > would add virtual functions HT and lookup for the function will be another HT lookup. > > image.png > > That for sure is better than trap for cpu, but enlarge memory usage at the moment. > > > --- > > Moreover, it allows us to keep both static and dynamic functions. > > function class::func(){} // static extension class:func() > function class->func(){} // dynamic function $class->func() > > > > --- > > this functions can be found dynamically and it seems alright: > > // a.php > use Models\User; > > function User::getName(){} > > // new User->getName is available here > > // b.php > > use Models\User; > > // new User->getName is NOT available here, because a.php wasn't loaded and here > User::getName isn't available > > // c.php > > namespace Stuff; > > include 'a.php'; > > // new User->getName here you can do it, because a.php was loaded and functions table was > adjusted with getName function > > // d.php > > use Stuff\Smth; > use Tools\Smth2; > > // if it's an app entrypoint > // autoloader loads c.php because of Smth file is found there > // c.php loads a.php > // the extension function User::getName is also available here > > // either is this file an entrypoint or not > // it stores the extension function in the class definition > // so Smth2 now can use the extension function, because it was loaded "by parent" > > > Very much not. The use construct has no bearing on > > autoloading currently. Autoloading happens only for classes and class-like things (interfaces, > > traits, enums). If a function is not found, PHP just crashes. Various solutions to this have been > > discussed over the years, none of which ever made it as far as a vote. > > Is this covered by the texts above? > > > In fairness, I think with universal opcache, preloading, and the increasing use of > > persistent processes, just skipping autoloading for functions and front-loading them via > > composer.json's "files" block is fine for the 80% case. But it feels like I am in > > the minority on that position. > > That's what we have now. Can't see any problems. > > > On Tue, Jun 10, 2025 at 11:11 PM Larry Garfield <larry@garfieldtech.com> wrote: >> On Tue, Jun 10, 2025, at 2:45 PM, Dmitry Derepko wrote: >> > Thanks for participating, Larry. >> > >> > On Mon, Jun 9, 2025 at 10:29 PM Larry Garfield <larry@garfieldtech.com> wrote: >> >> 2. Please link to a PR of your actual implementation. In context it looks like >> >> your branch comparison link is to the version you said didn't work, so it's not that >> >> helpful. >> > >> > Correct, I don't have another one. This is big feature, I need a lot of >> > time to implement it. I don't want to waste my time if we decide that >> > RFC won't pass at all. >> >> Understood. >> >> >> 3. The biggest question that has come up in the past (Ilija and I have discussed >> >> it at length) is, naturally, autoloading. How if at all do you address that? >> > >> > In the original message I mentioned use extension >> > construction. This >> > should be enough for solution, isn't it? >> >> Very much not. The use construct has no bearing on >> autoloading currently. Autoloading happens only for classes and class-like things (interfaces, >> traits, enums). If a function is not found, PHP just crashes. Various solutions to this have been >> discussed over the years, none of which ever made it as far as a vote. >> >> I toyed with the idea of having extension functions compile to a static method on a class >> as a way around this, but of course then you end up with a file-per-function, and the file name has >> to match not the function name, but whatever mangled class name gets generated. Not at all >> intuitive. >> >> In fairness, I think with universal opcache, preloading, and the increasing use of >> persistent processes, just skipping autoloading for functions and front-loading them via >> composer.json's "files" block is fine for the 80% case. But it feels like I am in >> the minority on that position. >> >> >> 4. The other big question was determining when to match a given "method" >> >> call to an extension function, when the type of a variable is not always known at compile time. How >> >> did you address this? >> > >> > Cannot understand the passage, could you explain more? >> >> <?php >> // index.php >> >> function Point.area(): int { >> return $this->x & $this->y; >> } >> >> function doStuff($p) { >> // At compile time, we don't know that $p is a Point. In fact, it may not be. >> // The function will allow any value here, even a non-object, so it doesn't know >> // if this should be compiled to Point__area($p) or left as is. >> print $p->area(); >> } >> >> The only way I could think of to handle that is to have a method call "trap" >> similar to class autoloading, that when hit checks at runtime "hey, this method didn't >> exist, but is there a used function that would match based on the >> runtime type of this value?" But Ilija felt that would be prohibitively slow. It would >> certainly be slower than just a function/method call since the trap takes time. >> >> And then we get into questions of inheritance, and, well, it gets even messier fast. >> >> One possibility that we riffed on during the pipes discussion (mostly off list, I think) >> was using +> for some combination of extension functions and Elixir-style first-arg pipe passing, >> so that $p+>area() would signal to the engine (compile time or runtime) that area() wasn't a >> method but a function that should get $p passed to it. That would solve the "trap" >> problem, but still doesn't address autoloading, the lack of compile time type knowledge, or how >> to differentiate between Point.area(), ShapeInterface.area(), Rect.area(), etc. >> >> --Larry Garfield > > > -- > Best regards, > Dmitrii Derepko. > @xepozz How does it handle late binding? (This is when a class extends/implements a class that doesn’t exist yet; so the compiler postpones actually creating the class until runtime when it can run the autoloader, if needed) should these functions also late bind in that case? — Rob

« previous php.internals (#127642) next »