13 ms·
Everything you need (and don't need) to know about PHP's type system
- untog 6y agoI have to say I’m impressed by how far PHP has come. I haven’t written any in years (well over a decade, even) but the commitment to improving a language many have written off as a dead end is laudable.
- jonny383 6y agoPHP rocks in 2020. Couple it with laravel or something and you get a solid platform to build a monolith-type web app with really fast performance.
- bnt 6y agoIsn’t Laravel the worst performing framework out there right now, like even Rails looks like a viable option in terms of speed?
- jonny383 6y agoRuby is slower than PHP7+ by orders of magnitude. I doubt it.
- amval 6y agoOrders of magnitude? Do you thibk that PHP is at least x100 times faster than Ruby?
- jonny383 6y agoAlright, maybe an exaggeration. But the difference is huge. https://benchmarksgame-team.pages.debian.net/benchmarksgame/fastest/php-yarv.html https://benchmarksgame-team.pages.debian.net/benchmarksgame/...
- tutfbhuf 6y agoWell that is a benchmark with a set of specific mathematical problems like calculating pi digits. I would rather compare Rails with Laravel e.g. in terms of requests per second or speed of json deserialization. See https://www.techempower.com/benchmarks/ https://www.techempower.com/benchmarks/ Symfony, Lumen and Rails seems to be somewhat equal in performance, but Laravel is a bit slower in respect to the benchmarked web related criterions.
- noir_lord 6y ago> Isn’t Laravel the worst performing framework out there right now. I'm more of a Symfony than Laravel guy but I've done both enough to know that application architecture and environment configuration has more of an impact than either framework's "performance" does. Silly things are slow in most web frameworks.
- fraktl 6y agoNo. Laravel performs quite nicely. Rails can't be compared to Laravel, it's slower by an order of magnitude, as mentioned previously. Any framework bears overhead, they all optimize programmer's time invested into solving the problem. It's cheaper to buy hardware and scale horizontally rather than swap languages and frameworks hunting for performance. PHP being synchronous by nature is what limits its performance, but we have Swoole that fixes it and makes it faster. For the ones who will google what Swoole is, some benchmarks I've done on my laptop show 5x (yes, 5 times, 500%) increase in performance when Laravel is ran via Swoole.
- tutfbhuf 6y ago> No. Laravel performs quite nicely. Rails can't be compared to Laravel, it's slower by an order of magnitude, as mentioned previously No, that's outright wrong. Please see the well respected techempower web benchmark: https://www.techempower.com/benchmarks/ https://www.techempower.com/benchmarks/ > For the ones who will google what Swoole is, some benchmarks I've done on my laptop show 5x (yes, 5 times, 500%) increase in performance when Laravel is ran via Swoole. Yup, that seems to be correct. What are the drawbacks of Swoole?
- fraktl 6y ago> No, that's outright wrong. Please see the well respected techempower web benchmark: https://www.techempower.com/benchmarks/ https://www.techempower.com/benchmarks/ I just notified the servers I've to manage (and my coworkers) that we're outright wrong and the load we're seeing is phantasm and that guy from internet told us so since he linked the well respected techempower benchmarks, which apparently reflect real world situation :)
- tutfbhuf 6y agoIf you and your co-workers have both Rails and Laravel in production and your Laravel applications performs better, then I have absolutely no doubt about that. However, there is no evidence that Rails is an order of magnitude slower than Laravel in general, quite the contrary, benchmarks indicating that (non-swoole) Laravel is slower.
- Can_Not 6y agoThe last time I looked at a rails-clone framework speed comparison chart rails was the slowest, with some Sinatra clones being the fastest.
- noir_lord 6y agoIt's gotten a lot better since I started using it ~2009 and now. 7.4 added typed properties. 8 is adding better caching, a jit and my favourite feature match() https://php.watch/versions/8.0#match-expression https://php.watch/versions/8.0#match-expression for all the enterprise heavy stuff I write a nicer cleaner and safer (by default) alternative to switch is going to make some code much cleaner to write and read and really that is what I care about more than almost anything else. That it also returns a value is just the cherry on top. I am so tired of reading bad code with poor intent that has no comments and no documentation that's written in the most counter intuitive way.
- admissionsguy 6y agoThe match expression is so elegant. For the past 10 years I've been puzzled by how verbose switch is.
- noir_lord 6y agoIt's better than switch for a lot of switch use cases, it's still not 'real' pattern matching but yeah I'm looking forwards to it.
- untog 6y agoMatch looks exactly how Rust’s match works and it’s one of my favourite parts of the language. Happy to see it elsewhere too.
- gwillz 6y agoThis is quite complete, definitely bookmarking for reference. I've been knee deep in PHP for the last 6 months after keeping it at arm's length for probably 10 years. It's really quite incredible how much it's improved and I think the type system is the major factor for me. It's not perfect but damn - I can get some stuff done really quick now.
- forgotmypw17 6y agoWhile we are on the subject, does anyone know of a way of having required variable declarations in PHP, similar to the way Perl's "use strict" works? This is one of my most common sources of bugs, and it is frustrating not having this be available, when it makes my life so much easier in Perl. Lately I've been thinking about doing something crazy like implementing my own variable system...
- notRobot 6y ago> Strict typing mode. In PHP the declare(strict_types = 1); directive enables strict mode. In strict mode, only a variable of exact type of the “type declaration” will be accepted, or a TypeError will be thrown. The only exception to this rule is that an integer may be given to a function expecting a float. https://www.brainbell.com/php/strict-type.html https://www.brainbell.com/php/strict-type.html
- paledot 6y agoWorth emphasizing that this directive applies per file, and affects functions called (not those defined) in that file. Not sure if there's a mechanical reason for that, but if I'm writing a new class I'd like some assurances that it's being used correctly. If I could enforce strict types on calling code, I could do away with a certain class of validation.
- zerocrates 6y agoThe point is supposed to be that once you write in a scalar typehint for a parameter, you don't need to do validation for it being the right type within the function: even if it's called from a non-strict context, that just means PHP will cast it before passing it. So you can avoid type checking code in your function but consumers can still use the more traditional and dynamic style of PHP if they want to. I can't quite think of the type of validation you'd be able to avoid with the sort of "inverted" strictness you're describing. Certainly I can think of issues people could have if not using strict types (basically, unexpected casts), but not things that you could actually validate from within the function.
- duskwuff 6y agoAdding a static analyzer (like Psalm [1]) to the mixture makes PHP's types much more powerful. Psalm can use docblock annotations to attach more complex types to functions and variables, including: * A "list" type representing a non-associative array * Types representing specific kinds of values, like numeric-string or non-empty-array, as well as exact values as types (like true and false, or string constants). * Typing on keys and values in arrays, e.g. array<class-string,int> for an array with class names as keys and integers as values * Complex typing on the contents of associative arrays, e.g. array{foo:int, bar:string} * Templated types on functions, like a function which returns an instance of a class whose name is passed in as a string: /** * @template T * @param T::class $class_name * @return T */ [1]: https://psalm.dev/ https://psalm.dev/
- mhitza 6y agoPsalm is nice, however I would suggest PHPStan as an alternative for people that encounter a lot of friction with Psalm. For example, in a project using doctrine I have to add a bunch of is null/@psal-mutation-free annotations. As all the methods can return null. However, if Psalm had support for something like phantom types, maybe I could tag entities returned from the database for whom certain fields are guaranteed to have values.
- slifin 6y agoAdding Phan to this conversation initially created by the creator of a PHP, now in the hands of TysonAndre who does an insane amount of good work on it
- noir_lord 6y agoFor users of the intellij family (idea or phpstorm). https://plugins.jetbrains.com/plugin/10215-php-inspections-ea-ultimate- https://plugins.jetbrains.com/plugin/10215-php-inspections-e... is amazing and well worth the price. It has a free variant which is still amazing but lacks all the inspections of the paid variant. https://plugins.jetbrains.com/plugin/7622-php-inspections-ea-extended- https://plugins.jetbrains.com/plugin/7622-php-inspections-ea...
- osrec 6y agoIt actually makes me really happy to see more positive comments on a thread about PHP. It is an incredible workhorse, and doesn't get the credit it deserves. I'm often amused by developers that revile PHP, while going on to use another language, which suffers from a similar set of problems to PHP, oftentimes with poorer performance and more complex toolchains. PHP deserves a little more love, imo.
- tutfbhuf 6y agoWe often have comments like "actually php is not that bad" and then people might think let's give it another try, only to find out that they came across all over the same quirks of language (design) and runtime behavior again. I think the main problem of php is that it's so inconsistent. I would rather prefer a bad language if it would happen to be at least very consistently so.
- bsdubernerd 6y agoI always used and use PHP because it gets the s$$$ done. But truth be told, the hate is deserved. It never was a particularly efficient language, which might not matter that much, but it was riddled with gotchas, warts and horrible solutions to many technical and social problems. Today PHP is faster than many alternatives, many of its warts got fixed, but I cannot brush off the fact that it's still based on a poorly-designed base and runtime library. I'm still using PHP when it makes sense, in the same way I'm still using perl where it makes sense.
- kyriakos 6y agoI agree with both statements, it gets shit done but has its rough edges. Its improving though and I doubt there's a perfect programming language out there. At the end of the day what matters are results and how quickly you went from idea to production and PHP is one of the good ones for that matter.
- 87zuhjkas 6y agoI think "rough edges" is an understatement. It has serious design flaws and inconsistencies which are probably never going to be fixed due to backwards compatibility. It's like C++ now, tons of language features are added over the years but non of them is able to repair the language, similar to a game of Jenga, the tower will collapse eventually.
- chx 6y agoMinor nits: 1. "they all inherit from stdClass" -- this is simply not true 2. callables should've mentioned anonymous functions 3. a special typed value can't be casted to anything. -- this is not true, NULLs can be casted to anything (it becomes 0, "", array() ) and even resources can be casted to anything with dubious utility value. 4. casting should mention the intval() , strval() , doubleval() functions 5. php does not support explicit type definition in variable declaration -- PHP 7.4 however supports typed properties. https://wiki.php.net/rfc/typed_properties_v2 https://wiki.php.net/rfc/typed_properties_v2
- nawarian 6y agoI'll definitely edit the post adding the relevant bits you mentioned. Two special notes: About 1. stdClass, you're right and I don't know why I just took it for granted without even testing. My Bad. About 3. casting special types, you're right again. I didn't phrase it properly. Casting null to other types won't yield errors and casting resources too. Their values are normally nothing we should rely on, but doesn't mean one "can't" perform such casts. Thanks a lot for your comments, they are incredibly helpful! Cheers!
- paledot 6y ago> Important to notice that casting an array with numeric keys into an object is valid, but one can't dereference its value because property names may not start with numbers. Not true, actually. The (admittedly obscure) syntax to access a property beginning with a numeral is `$obj->{0}`. Usually when this happens it's because someone was trying to be clever with JSON.
- flir 6y agoThere's another way to get a variable starting with a numeral - abusing extract(), I think.
- paledot 6y agoI've seen a few workarounds, each worse than the last, including casting back to array, round-tripping through JSON with the array flag set, and reflection. Hence the public service announcement that this is perfectly doable with the correct syntax.
- aslamc 6y agoIs there a good reason to still use php when you can use hacklang (https://hacklang.org/ https://hacklang.org/) which has much stronger type system. Some would even call it php++.
- simonhamp 6y agoA lot of what Hack introduced to the PHP community has become available in suitably forward-thinking ways to allow for a sensible amount of backwards compatibility and are opt-in. For example, you can set strict typing on a per-file basis. `declare(strict_types=1);` I believe that the performance difference between the two is negligible now too. So it really just comes down to personal preference/platform legacy. But Hack is on a different path which is potentially going to make it harder to share code between PHP and Hack. PHP still has by far the larger community. Given the choice today, I’d run with PHP.
- asddubs 6y agothe only thing that sucks about strict typing is that there's no way to toggle it globally. so if you want to transition a codebase that's simultaneously actively being developed in other ways, you have to mess around with scripts that append it to the start of all php files/remove it again
- nawarian 6y agoNothing that tools like Rector can't help you with. I believe this extra step is incredibly important, given most of your dependencies you won't control and forcing strict types to them is not very clever IMO.
- asddubs 6y agoI guess it wouldn't work if your dependencies weren't easily seperable from the rest of the code. in this case there are no dependencies, it's all custom cobbled together, for better or worse
- 6y ago
- wolco 6y agoMain takeaway: strict types won't make your code faster! It may make it slightly slower
- fennecfoxen 6y agoThe point of strict types is generally not speed, but rather, to make your code more correct.
- chiefalchemist 6y agoCorrect? I'd probably say predictable.
- fennecfoxen 6y agoEh. If MyPy complains that I'm passing an `Optional[Entity]` into a method where only an `Entity` can go, it's just helped me avoid a runtime error when I try to get `entity.name`. Not sure what the exact PHP equivalent is, but there's all sorts of bugs you can easily introduce if you're not careful with types.
- wolco 6y agoPHP doesn't compile so all errors become runtime errors.
- fennecfoxen 6y agoIt is nice that you are trying to inform me but I am already aware of the information that you bring and your decision to bring it makes it seem to me as if you are uninformed. It is possible to conduct static analysis of a source code file that is not "compilation" in the sense that you would otherwise see with Java or C. Python's not really any different than PHP in this regard.
- stunt 6y agoYeah but should use static analysis tools in your CI/CD and development workflow when using an interpreted language. That's a must have. So better typing can definitely help to catch those before pushing and running your code.
- choma 6y agoCompletely unrelated but, if the site owners read this: pleas, make the CSS ::selection a different color from the background, please!!
- nawarian 6y agoThanks for pointing this out. It annoyed me a lot as well. The whole "dark mode" css was a "better than nothing" thing, and now I'm collecting the "must fix" things. This is definitely on the list! That said: the website is open source, feel free to submit a PR if you find time before I do :D