Hello, internals!
Recently I was implementing some collections and realized that I cannot use
ArrayAccess
for immutable collections without throwing
BadMethodCallException
in offsetSet
and offsetUnset
. I also cannot
have an interface ReadonlyCollection extends ArrayAccess
, because
offsetSet
and offsetUnset
are mutators and have TValue
in a
contravariant position.
Here's the idea: let's extract ArrayAccess::offsetExists
and
ArrayAccess::offsetGet
methods into a separate ArrayAccessRead
interface (name can be different) and allow read operations $exists = isset($object['key'])
and $value = $object['key']
for objects of classes
that implement this interface. ArrayAccess
will then extend
ArrayAccessRead
and add the remaining 2 methods. Looks like this change
should not break backward compatibility.
interface ArrayAccessRead
{
public function offsetExists(mixed $offset): bool;
public function offsetGet(mixed $offset): mixed;
}
interface ArrayAccess extends ArrayAccessRead
{
public function offsetSet(mixed $offset, mixed $value): void;
public function offsetUnset(mixed $offset): void;
}
// then interfaces of the doctrine/collections package might look like this:
namespace Doctrine\Common\Collections;
interface ReadableCollection extends Countable, IteratorAggregate,
ArrayAccessRead {}
interface Collection extends ReadableCollection, ArrayAccess {}
--
Regards, Valentin Udaltsov
On Mon, May 27, 2024 at 7:16 AM Valentin Udaltsov <
udaltsov.valentin@gmail.com> wrote:
Hello, internals!
Here's the idea: let's extract
ArrayAccess::offsetExists
and
ArrayAccess::offsetGet
methods into a separateArrayAccessRead
interface (name can be different) and allow read operations$exists = isset($object['key'])
and$value = $object['key']
for objects of classes
that implement this interface.ArrayAccess
will then extend
ArrayAccessRead
and add the remaining 2 methods. Looks like this change
should not break backward compatibility.
Please check this: https://externals.io/message/122609#122609 where Gina
analyzed and proposed a solution for this.
It looks like the DimensionReadable is exactly the same thing. Maybe also
DimensionFetchable if you consider returning by reference.
Maybe the improvement can be done in smaller incremental steps, but I think
it's better to agree on a complete solution for splitting ArrayAccess.
Regards,
Alex
On Mon, May 27, 2024 at 14:21 Alexandru Pătrănescu drealecs@gmail.com
wrote:
On Mon, May 27, 2024 at 7:16 AM Valentin Udaltsov <
udaltsov.valentin@gmail.com> wrote:Hello, internals!
Here's the idea: let's extract
ArrayAccess::offsetExists
and
ArrayAccess::offsetGet
methods into a separateArrayAccessRead
interface (name can be different) and allow read operations$exists = isset($object['key'])
and$value = $object['key']
for objects of classes
that implement this interface.ArrayAccess
will then extend
ArrayAccessRead
and add the remaining 2 methods. Looks like this change
should not break backward compatibility.Please check this: https://externals.io/message/122609#122609 where Gina
analyzed and proposed a solution for this.
It looks like the DimensionReadable is exactly the same thing. Maybe also
DimensionFetchable if you consider returning by reference.Maybe the improvement can be done in smaller incremental steps, but I
think it's better to agree on a complete solution for splitting ArrayAccess.Regards,
Alex
Wow! That's a great RFC with thorough analysis and an awesome proposal.
Forget about my email 😄. Looking forward to news from Gina.
Regards, Valentin Udaltsov