On Fri, 01 Oct 2010 09:38:19 +0100, Adam Harvey <ahar...@php.net> wrote:

On 30 September 2010 21:33, Adam Harvey <ahar...@php.net> wrote:
I've just written an RFC (with a patch against trunk) to implement a
Comparable interface similar to that in Java — in effect, allowing
object instances to be compared with semantics defined in userspace.
This is admittedly at the lower end of RFC-worthy proposals, but it's
a good system, and I'd like to see it used a little more. Plus, it's
good practice for the more interesting stuff to come. :)

I've updated the RFC with a fresh patch that doesn't involve SPL at
all and attempted to incorporate some of the questions and answers so
far into the RFC. I've also added a section for concerns with the RFC;
I've attempted to distil the concerns I've seen so far, but please
feel free to edit that list if specific concerns are misrepresented or
unrepresented.

Links:

RFC: http://wiki.php.net/rfc/comparable
Patch v2: http://www.adamharvey.name/patches/comparable-v2.diff.txt


Here's a new concern: I find a bad idea to call compareTo *before* 'compare_objects'. This means that if in your internal class you define your own comparison logic with 'compare_objects', you cannot make sure the userland subclasses won't completely replace your logic by implementing Comparable. So to prevent this you'd have to implement 'Comparable' yourself...

The low level feature should have priority (look at e.g. Countable vs count_objects); you could always in your 'compare_objects' check for the interface and call it if you want to allow userspace subclasses to replace the comparison logic.

The RFC says:

How do you interact with 'get' and 'cast_object'/'__tostring'?

The tests for whether the operands implement Comparable occur before
any potential calls to get and cast_object.

So basically this means that 'get' and 'cast_object' will never be called of an object $a will never be called if it's being compared to a Comparable object $b, right?

This is not a very good idea because it puts the responsibility to deal correctly with proxy objects and scalar castable objects on the part of the implementor of the compareTo method.

Tis means people implementing compareTo natively will almost never get it right. Let's say they want to make their object comparable with integers. You pass a proxy object that yields integers. Now the native implementor sees an object and must remember to check for the existence of 'get' and 'cast_object' and call them if necessary. Right.

For userland implementations, the situation is not much better; the implementor for compare would (most likely) have to do an explicit cast to the type he wants to compare with and, of course, using stuff like 'gettype' would probably result in wrong behavior.

TL;DR: 'get' and 'cast_object' should be checked for and, if necessary, called first.

If both $a and $b are objects with different compare functions,
how it is determined whose function is used? Note that operators
like == are assumed to be commutative, and less/more operators
are assumed to be commutative in pairs, like above.

The left operand wins, so $a.

At least in Java, it's clear this is happening because you call a.compareTo(b). This is a dangerous feature... In my opinion, if they have different compareTo implementations, they shouldn't be compared.

--
Gustavo Lopes

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

Reply via email to