Hello,

From the RFC:

> If the left operand produces a TypeError due to the parameter types listed in 
> the implementation, the operation is not retried with the right operand and 
> the error is instead returned immediately. This is to help developers 
> encounter errors in their program logic as early as possible.

This feels wrong if I understand correctly.

Let’s say I create a class A and I want to add support for "2 / new A()", which 
by default does not work.

I can do
class A
{
  operator /(int $other, OperandPosition $operandPos): mixed
 {
    return "example";
 }
}

Now someone wants to build on my work, and add a class B that supports "new A() 
/ new B()".

class B
{
  operator /(A $other, OperandPosition $operandPos): mixed
 {
    return "example";
 }
}

This will not work because it will first try A->{'/'}(B) that throws a 
TypeError? So it means what I was able to do for floats, cannot be done for my 
new classes afterwards? This is inconsistent I think. It also means it is not 
possible to extend any existing class with operators interacting with a new 
class, meaning you can only use operators among classes aware of each other, 
most likely from the same package/library.

Also, this was stated already I think but I did not see an answer, from RFC 
example:
> class Matrix {
>     public function __construct(readonly public array $value) {}
>  
>     public operator *(Matrix $other, OperandPosition $operandPos): Number
>     {
>         if ($operandPos == OperandPosition::LeftSide) {
>             // Count of my columns needs to match
>             // count of $other rows
>         } else {
>             // Count of my rows needs to match
>             // count of $other columns
>         }
>     }
> }

The second branch of the if is dead code, as $matrix1 * $matrix2 will always 
call $matrix1->{'*'}($matrix2, LeftSide) and never the other way around.
This means that $operandPos is useless in all cases where operators are only 
typed againts the same type, and points to this design solution being wrong.

There is «Why not interfaces?» in the FAQ, does that mean that operators cannot 
be added in interfaces? This is not stated clearly in the RFC.

Also, it is not clear if operator overload will affect comparison operations 
used in core functions such as in_array, sort and so on.
Does implementing operator == allows using in_array to find an object in an 
array?
Which of these internal functions use == and which use ===, which is not 
overloadable?
Does implementing operator <=> allows sorting of arrays containing my objects?

Côme

--
PHP Internals - PHP Runtime Development Mailing List
To unsubscribe, visit: https://www.php.net/unsub.php

Reply via email to