Req #71271 [Wfx]: Allow final abstract class {}
| From: | requinix@php.net | Date: | Sat, 16 May 2020 20:38:54 +0000 |
| Subject: | Req #71271 [Wfx]: Allow final abstract class {} | ||
| References: | 1 | Groups: | php.bugs |
| Request: | Send a blank email to php-bugs+get-227068@lists.php.net to get a copy of this message | ||
Edit report at https://bugs.php.net/bug.php?id=71271&edit=1
ID: 71271
Updated by: requinix@php.net
Reported by: andreas at dqxtech dot net
Summary: Allow final abstract class {}
Status: Wont fix
Type: Feature/Change Request
Package: Class/Object related
PHP Version: 7.0.2RC1
Block user comment: N
Private report: N
New Comment:
https://wiki.php.net/rfc/howto
It's been four years so that might be enough time for people to have reconsidered. But like I
said last time, note that "static" classes had more support than "abstract
final" classes.
Previous Comments:
------------------------------------------------------------------------
[2020-05-16 13:42:20] rnealxp at yahoo dot com
I went to submit this legitimate request that php should make allowance for "final abstract
class". It is not right that this previous request was declined. It makes very good sense to
have a class that both cannot be extended and that cannot be instantiated, since it contains only
static functions (for use in organizing a code-library). It is a no-brainer.
------------------------------------------------------------------------
[2016-01-04 07:29:46] andreas at dqxtech dot net
> Your abstract+final idea was one of the options (the first one, even) but it looks like full
> static classes had more support.
Well, as I understand the RFC, and the discussion on the PR, the plan was to make the language
prevent you from creating non-static methods in the class. So it would do more than just allow the
keyword combo. While this would make sense in some way, it also would break user expectations, imo.
A user should expect that combining two known keywords just has the combined effects of each
keyword, but no additional extra effect.
If an extra effect is intended, I would rather opt for the other option, the "static
class", and allow users to make it a "final static class" if they wish.
This appears attractive at first sight, but then there is the debate of whether to make the
"static" keyword implicit or explicit. Whichever option is chosen, it will be a new thing
for people to learn an remember.
The combo of abstract + final may look ugly, but it is a combination of well-known and
well-understood language features, so it would be very predictable - if it is implemented without
any creative extra behavior.
Finally, I don't see why utility classes are considered an anti-pattern. I think they are
perfectly fine.
Global functions, even with namespace + autoloading, would mean to have a separate directory
structure of source files for procedural code, in addition to the PSR-4 or PSR-0 directory structure
for classes.
And the function autoloading would be yet another thing to learn and babysit.
Besides: No matter if you like them or not, utility classes are being used today.
Currently I let my utility classes "extends UtilBase". UtilBase has a "final private
function __construct() {}", which maybe is even better than "final abstract class".
But it means I have a number of these "UtilBase" classes, up to one per package.
> After all, if you can't instantiate the class and you can't extend it, what else can
> you do with it besides use static members?
Well.. generally I only put static members into my utility classes.
But, for the record, I currently have a use case where some of these non-instantiable classes
inherit from an interface, with non-static methods.
This is only for a discovery mechanism, which will assume that an annotated static method will
return an object which then generates objects of the provided interface. So I am using the interface
like a meta-tag.
This is quite exotic, obviously, and not the common way to use interfaces...
> You're free to bring up the subject on the internals list, naturally. However it's
> only been a year so I wouldn't expect opinions to have changed much.
Maybe I will :)
------------------------------------------------------------------------
[2016-01-04 06:16:04] requinix@php.net
Original RFC thread: http://marc.info/?l=php-internals&m=141706013928872&w=2
Thread renamed: http://marc.info/?l=php-internals&m=141744239115034&w=2
Vote: http://marc.info/?l=php-internals&m=141840083023519&w=2
Your abstract+final idea was one of the options (the first one, even) but it looks like full static
classes had more support. After all, if you can't instantiate the class and you can't
extend it, what else can you do with it besides use static members?
You're free to bring up the subject on the internals list, naturally. However it's only
been a year so I wouldn't expect opinions to have changed much.
------------------------------------------------------------------------
[2016-01-04 05:50:48] andreas at dqxtech dot net
It seems this is the discussion:
https://github.com/php/php-src/pull/923
------------------------------------------------------------------------
[2016-01-04 05:43:10] andreas at dqxtech dot net
Is there any discussion I could have a look at, that explains why the RFC was discarded by most
participants?
Also, what I propose is not really the same, it is much simpler: Allow the combination of the two
keywords, with the regular natural consequences.
abstract: Cannot instantiate.
final: Cannot inherit.
I do NOT propose that a final + abstract class should only have static members.
I think it would be a bad idea to enforce this on the language level.
On the other hand, an IDE could very well notify people about the pointlessness of non-static
methods within a final abstract class.
Unlike the RFC, this simple proposal adds no confusion and no magic. Everything will behave as one
would expect.
------------------------------------------------------------------------
The remainder of the comments for this report are too long. To view
the rest of the comments, please view the bug report online at
https://bugs.php.net/bug.php?id=71271
--
Edit this bug report at https://bugs.php.net/bug.php?id=71271&edit=1