develooper Front page | perl.perl6.language | Postings from July 2006

Re: ===, =:=, ~~, eq and == revisited (blame ajs!)

Thread Previous | Thread Next
From:
Yuval Kogman
Date:
July 13, 2006 07:37
Subject:
Re: ===, =:=, ~~, eq and == revisited (blame ajs!)
Message ID:
20060713143619.GA19536@woobling.org
On Thu, Jul 13, 2006 at 00:55:30 -0700, Darren Duncan wrote:

> So, in the general case, it would seem best if the binary operator === was just an ordinary method that each class provides, rather than requiring classes to defined a .id.  Or 
> in addition to this to help with performance, a .id can exist anyway that optionally returns an appropriate hash of an object.

But what is the benefit here?

Keying by object is a difficult topic. In Perl 5 you sometimes want
to key by refaddr (more often than not) because you are associating
new metadata with the instance, that does not belong inside the
instance.

On the other hand you also often want something like "$obj" to be
the key, if it can properly stringify, so that an object like a
currency:

	my $x = Currency.new( code => "USD" );
	my $y = Currency.new( code => "USD" );

	$hash{$x} = 1;

	say $hash{$y}; # 1

will DWIM. But this really depends on both the item being used,
*and* the way it is being used.

So I can see the value of making the second type of keying possible
and easy with an .id method (which at the very lowest level can
probably just emit e.g. a YAML representation of an object to ensure
uniqueness, if performance is *really* not an issue).

But this does not relate to equality, it's only useful for defining
it.

We were essentially questioning the reason === is specced to behave
as it currently does, because we feel that it's not very useful if
it's not clear cut that it should either *really* compare, or not
compare at all. And if it doesn't compare, we'd like a deep
comparison operator in S03.

> Built-in mutable types, like Array or Hash, would not override the Object-defined ===, which is equivalent to =:=, nor the built-in .id, which returns the object itself.  This 
> is reasonable in practice because the contents of those containers could be changed at any time, especially if the containers are aliased to multiple variables that are outside 
> of the testing code's control.  The only thing that can be guaranteed to be constant over time is that whether or not an object is itself, as determined by =:=.  By contrast, if 
> === were to do a deep copy with mutable types, the results could not be trusted to be repeatable because the moment after === returns, the container's value may have changed 
> again, so actions done based on the === return value would be invalid if they assumed the value to still be the same at that time, such as if the mutable type was used as a hash 
> key and was to be retrievable by its value.


The behavior for arrays is useless to me, because I already have
=:=. I can write a hybrid ===/=:= operator for very special cases,
but 99% of the time I want to ask "do these (arrays|hashes) contain
the same values *right now*?"

> User defined types can choose on their own whether to override === and/or .id or not, and they would use their own knowledge of their internal structures to do an appropriate 
> deep comparison.  There is no need to try to generate some kind of unique numerical .id for arbitrarily complex objects.

That creates a mess - sometimes objects compare themselves based on
their value, and sometimes based on their containing slot. These are
very different semantics.


-- 
  Yuval Kogman <nothingmuch@woobling.org>
http://nothingmuch.woobling.org  0xEBD27418


Thread Previous | Thread Next


nntp.perl.org: Perl Programming lists via nntp and http.
Comments to Ask Bjørn Hansen at ask@perl.org | Group listing | About