[RFC] Userspace operator overloading

  108608
February 15, 2020 22:05 jan.h.boehmer@gmx.de
Hi internals,

based on the discussions here (https://externals.io/message/108300) and here
(https://github.com/php/php-src/pull/5156), I have created a proper RFC for
userspace operator overloading:
https://wiki.php.net/rfc/userspace_operator_overloading

The main differences to my original concept, is the removed __compare()
method (comparison overloading is a complex topic and should be handled in a
different RFC) and the possibility to signal that the operator handler does
not support the given types (by typehints or returning a special value).
This way, only one of both objects has to know about the other type. This
should expand the use case of operator overloading compared to my old
concept.

What do you think about the RFC?

Some discussion points, I can think of, would be the naming of the methods
(maybe naming them after the operator symbol and not the arithmetical
operation they represent, e.g. __plus instead of __add) or putting the
methods inside of interfaces like done for ArrayAccess (But I don’t see any
advantage in doing so, as it is very difficult grouping different operators
in a single interface usefully. Also, operators can accept and return
different types, so there is no real common interface between classes you
could rely on).
Furthermore, maybe the idea of allowing operator overloading in general
should be discussed as it is sometimes considered an anti-pattern (e.g. the
usage of '<<' for outputting a string in C++). On the other hand there are
many languages and libraries where operator overloading is used successfully
(e.g. numpy in Python).

Regards,
Jan Böhmer
  108612
February 16, 2020 01:17 marandall@php.net (Mark Randall)
On 15/02/2020 22:05, jan.h.boehmer@gmx.de wrote:
> Hi internals, > What do you think about the RFC?
"If an operator is used with an object that does not overload this operator, an NOTICE is triggered, which gives the user a hint about the method that has to be overloaded. For backward compatibility objects, which do not overload the operator, are converted to integer 1 (current behavior)." Noooo :( Notices are the enemy of all that is great and good. If operator overloading is going to become a first-class feature then it should be treated as such, and attempting overloading operators on objects that don't have the relevant method available should trigger an Error. -- Mark Randall marandall@php.net
  108614
February 16, 2020 01:54 rowan.collins@gmail.com (Rowan Tommins)
On 15 February 2020 22:05:52 GMT+00:00, jan.h.boehmer@gmx.de wrote:
>Some discussion points, I can think of, would be the naming of the >methods >(maybe naming them after the operator symbol and not the arithmetical >operation they represent, e.g. __plus instead of __add) or putting the >methods inside of interfaces like done for ArrayAccess
As I mentioned earlier [1] I think the answers to both of these questions depend on a fundamental philosophical question about what you're overloading: - The groups of operations which exist for built-in types e.g. the arithmetic operations overloaded by GMP; or string operations overloaded by an object with enhanced Unicode functionality. - The individual symbolic operators, with no intrinsic meaning - e.g. overloading . for concatenation on strings but dot-product for vectors; or a DSL overloading << and >> for "into" and "out of". I think it would benefit the RFC to take a stance on that question, and build the feature around it. [1] https://news-web.php.net/php.internals/108347 -- Rowan Tommins [IMSoP]
  108615
February 16, 2020 05:07 smalyshev@gmail.com (Stanislav Malyshev)
Hi!

> - The individual symbolic operators, with no intrinsic meaning - e.g. > overloading . for concatenation on strings but dot-product for > vectors; or a DSL overloading << and >> for "into" and "out of".
Please no. I know it looks fancy and some languages love it, but for a person not in on the joke reading such code is a nightmare - it's basically gibberish until you learn all the types and which meaning each of the types assigns to operators. I mean, I could be maybe talked into having users overload "+" to mean "add some kind of objects that are like numbers but not actually integers" because my intuition still works there even if I don't know the exact type. But if someone thinks it's super-cool to override + to make it add element to the cache object - please no. It's way worse than just using plain old ->addObject(). You may save couple of keystrokes and make your code completely incomprehensible for people who come after you. I know DSLs have its niche but I seriously doubt average PHP user implements a lot of DSLs that are required to work natively on PHP engine. -- Stas Malyshev smalyshev@gmail.com
  108617
February 16, 2020 10:31 rowan.collins@gmail.com (Rowan Tommins)
On 16 February 2020 05:07:03 GMT+00:00, Stanislav Malyshev <smalyshev@gmail.com> wrote:
>Hi! > >> - The individual symbolic operators, with no intrinsic meaning - e.g. >> overloading . for concatenation on strings but dot-product for >> vectors; or a DSL overloading << and >> for "into" and "out of". > >Please no. I know it looks fancy and some languages love it, but for a >person not in on the joke reading such code is a nightmare
:) I know you're not alone in that feeling. If it turns out this is the majority view, I think it answers a couple of open questions: Overload methods should definitely be named after operations, not symbols, to remind people they are implementing addition, not giving new meaning to + They should probably be grouped into interfaces, which this RFC has so far resisted. How often does it make sense for a type to support addition but not subtraction, or multiplication but not division? Even more clearly, if a type claims to implement bitwise OR but not bitwise AND, NOT, and XOR, something is definitely fishy. You can't stop people using overloading DSL-style, but you can make it obvious that it's not the intention of the feature (if we agree that it's not the intention; maybe some people here are really hoping to use it that way?) Regards, -- Rowan Tommins [IMSoP]
  108619
February 16, 2020 12:28 george.banyard@gmail.com ("G. P. B.")
On Sat, 15 Feb 2020 at 23:06, boehmer@gmx.de> wrote:

> Hi internals, > > based on the discussions here (https://externals.io/message/108300) and > here > (https://github.com/php/php-src/pull/5156), I have created a proper RFC > for > userspace operator overloading: > https://wiki.php.net/rfc/userspace_operator_overloading > > The main differences to my original concept, is the removed __compare() > method (comparison overloading is a complex topic and should be handled in > a > different RFC) and the possibility to signal that the operator handler does > not support the given types (by typehints or returning a special value). > This way, only one of both objects has to know about the other type. This > should expand the use case of operator overloading compared to my old > concept. > > What do you think about the RFC? > > Some discussion points, I can think of, would be the naming of the methods > (maybe naming them after the operator symbol and not the arithmetical > operation they represent, e.g. __plus instead of __add) or putting the > methods inside of interfaces like done for ArrayAccess (But I don’t see any > advantage in doing so, as it is very difficult grouping different operators > in a single interface usefully. Also, operators can accept and return > different types, so there is no real common interface between classes you > could rely on). > Furthermore, maybe the idea of allowing operator overloading in general > should be discussed as it is sometimes considered an anti-pattern (e.g. the > usage of '<<' for outputting a string in C++). On the other hand there are > many languages and libraries where operator overloading is used > successfully > (e.g. numpy in Python). > > Regards, > Jan Böhmer > > -- > PHP Internals - PHP Runtime Development Mailing List > To unsubscribe, visit: http://www.php.net/unsub.php > > Just as a FYI, I'll vote No to this RFC regardless of arguments as I find
operator (and method) overloading a bad idea in general. Moreover, the only ones I am a tiny bit less reluctant to overload are the mathematical operators. However, one of the major reasons to want to have this seems to add better support for Matrices and Complex number which can already be done at the extension/engine level. Best regards George P. Banyard