Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > comp.lang.python > #74240
| Date | 2014-07-09 18:17 +1000 |
|---|---|
| From | Cameron Simpson <cs@zip.com.au> |
| Subject | Re: Proposal: === and !=== operators |
| References | <53bce8a3$0$2746$c3e8da3$76491128@news.astraweb.com> |
| Newsgroups | comp.lang.python |
| Message-ID | <mailman.11681.1404893854.18130.python-list@python.org> (permalink) |
On 09Jul2014 07:00, Steven D'Aprano <steve@pearwood.info> wrote:
>At the moment, Python has two (in)equality operators, == and != which
>call __eq__ and __ne__ methods. Some problems with those:
>
>* Many people expect == to always be reflexive (that is, x == x for
> every x) but classes which customise __eq__ may not be.
I'm presuming this proposal is fallout from the Nan anecdotes, since NaN !=
Nan?
The language spec is at least up front about it, I thought. It could be
plainer, but at least it says:
Furthermore, some types (for example, function objects) support only a
degenerate notion of comparison where any two objects of that type are
unequal.
which implies nonreflexivity.
Returning to Nan, I had thought it was an explicit design choice in IEEE
floating point that NaN != NaN so that in (hypothetically) common cases results
won't accidentally issue truthiness in the vein of propagating evaluation
errors.
Personally I'd go for Nan == Nan raising a ValueError myself, but that is a
bikeshed I lack the expertise to paint.
Anyway, I thought it is a design feature that a class can arrange for
nonreflexivity in ==. Surprising, maybe, but wouldn't use of such a special
class be known to the user?
Have we got some examples of people using nonreflexive == classes and being
burnt? Aside from Nan, which I'd argue is a well known special case, or should
be.
>* The == operator requires __eq__ to return True or False
> (or NotImplemented) and raises TypeError if it doesn't, which
> makes it impossible to use == with (say) three-valued or fuzzy
> logic.
In the Python 3.4.0 docs the __eq__ etc methods have this paragraph:
A rich comparison method may return the singleton NotImplemented if it does
not implement the operation for a given pair of arguments. By convention,
False and True are returned for a successful comparison. However, these
methods can return any value, so if the comparison operator is used in a
Boolean context (e.g., in the condition of an if statement), Python will call
bool() on the value to determine if the result is true or false.
and some tests with 2.7.8 and 3.4.1:
% python
Python 2.7.8 (default, Jul 3 2014, 06:13:58)
[GCC 4.2.1 Compatible Apple LLVM 5.1 (clang-503.0.40)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> class O(object):
... def __eq__(self, other): return 9
...
>>> o=O()
>>> o == o
9
% python3.4
Python 3.4.1 (default, May 21 2014, 01:39:38)
[GCC 4.2.1 Compatible Apple LLVM 5.1 (clang-503.0.40)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> class O(object):
... def __eq__(self, other): return 9
...
>>> o=O()
>>> o == o
9
I don't see this type constraint you describe.
>I propose:
>
>* The == operator be redefined to *always* assume reflexivity, that
> is, it first compares the two arguments using `is` before calling
> the __eq__ methods.
Won't this slow down every == test?
>* That's a backwards-incompatible change, so you need to enable it
> using "from __future__ import equals" in Python 3.5, and then to
> become the default behaviour in 3.6.
>
>* To support non-reflexive types, allow === and !=== operators, which
> are like == and != except they don't call `is` first.
[...]
I don't like the spelling. They seem very easy to misuse as typos of
conventional == and !=, and not visually very different.
Cheers,
Cameron Simpson <cs@zip.com.au>
55 mph is fast enough to get you killed, but slow enough to make you think
you're safe. - The Gumball Rally
Back to comp.lang.python | Previous | Next — Previous in thread | Next in thread | Find similar | Unroll thread
Proposal: === and !=== operators Steven D'Aprano <steve@pearwood.info> - 2014-07-09 07:00 +0000
Re: Proposal: === and !=== operators Chris Angelico <rosuav@gmail.com> - 2014-07-09 17:21 +1000
Re: Proposal: === and !=== operators Steven D'Aprano <steve@pearwood.info> - 2014-07-09 09:17 +0000
Re: Proposal: === and !=== operators Rustom Mody <rustompmody@gmail.com> - 2014-07-09 09:20 -0700
Re: Proposal: === and !=== operators Ian Kelly <ian.g.kelly@gmail.com> - 2014-07-09 11:50 -0600
Re: Proposal: === and !=== operators Cameron Simpson <cs@zip.com.au> - 2014-07-10 09:16 +1000
Re: Proposal: === and !=== operators Johannes Bauer <dfnsonfsduifb@gmx.de> - 2014-07-12 13:54 +0200
Re: Proposal: === and !=== operators Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2014-07-12 16:35 +0000
Re: Proposal: === and !=== operators Chris Angelico <rosuav@gmail.com> - 2014-07-13 02:54 +1000
Re: Proposal: === and !=== operators Roy Smith <roy@panix.com> - 2014-07-12 16:39 -0400
Re: Proposal: === and !=== operators Johannes Bauer <dfnsonfsduifb@gmx.de> - 2014-07-12 20:14 +0200
Re: Proposal: === and !=== operators Chris Angelico <rosuav@gmail.com> - 2014-07-13 09:01 +1000
Re: Proposal: === and !=== operators Roy Smith <roy@panix.com> - 2014-07-12 19:06 -0400
Re: Proposal: === and !=== operators Chris Angelico <rosuav@gmail.com> - 2014-07-13 09:15 +1000
Re: Proposal: === and !=== operators Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2014-07-13 04:48 +0000
Re: Proposal: === and !=== operators Cameron Simpson <cs@zip.com.au> - 2014-07-09 18:17 +1000
Re: Proposal: === and !=== operators Steven D'Aprano <steve@pearwood.info> - 2014-07-09 09:02 +0000
Re: Proposal: === and !=== operators Chris Angelico <rosuav@gmail.com> - 2014-07-09 19:23 +1000
Re: Proposal: === and !=== operators Devin Jeanpierre <jeanpierreda@gmail.com> - 2014-07-09 05:01 -0700
Re: Proposal: === and !=== operators Roy Smith <roy@panix.com> - 2014-07-09 08:27 -0400
Re: Proposal: === and !=== operators Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2014-07-09 12:48 +0000
Re: Proposal: === and !=== operators Tim Chase <python.list@tim.thechases.com> - 2014-07-09 13:05 -0500
Re: Proposal: === and !=== operators Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2014-07-10 01:10 +0000
Re: Proposal: === and !=== operators Ian Kelly <ian.g.kelly@gmail.com> - 2014-07-09 12:31 -0600
Re: Proposal: === and !=== operators Roy Smith <roy@panix.com> - 2014-07-09 16:47 -0400
Re: Proposal: === and !=== operators Ethan Furman <ethan@stoneleaf.us> - 2014-07-09 05:43 -0700
Re: Proposal: === and !=== operators Robert Kern <robert.kern@gmail.com> - 2014-07-09 16:27 +0100
Re: Proposal: === and !=== operators Alex Burke <alexjeffburke@gmail.com> - 2014-07-10 18:33 +0200
Re: Proposal: === and !=== operators Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2014-07-12 03:30 +0000
Re: Proposal: === and !=== operators Alan Bawden <alan@scooby-doo.csail.mit.edu> - 2014-07-12 01:07 -0400
Re: Proposal: === and !=== operators Torsten Bronger <bronger@physik.rwth-aachen.de> - 2014-07-12 08:05 +0200
Re: Proposal: === and !=== operators Torsten Bronger <bronger@physik.rwth-aachen.de> - 2014-07-12 08:14 +0200
Re: Proposal: === and !=== operators Chris Angelico <rosuav@gmail.com> - 2014-07-12 16:06 +1000
Re: Proposal: === and !=== operators Ethan Furman <ethan@stoneleaf.us> - 2014-07-11 23:11 -0700
Re: Proposal: === and !=== operators Chris Angelico <rosuav@gmail.com> - 2014-07-12 16:39 +1000
Re: Proposal: === and !=== operators Marko Rauhamaa <marko@pacujo.net> - 2014-07-12 10:06 +0300
Re: Proposal: === and !=== operators Ethan Furman <ethan@stoneleaf.us> - 2014-07-11 23:53 -0700
Re: Proposal: === and !=== operators Chris Angelico <rosuav@gmail.com> - 2014-07-12 17:25 +1000
Re: Proposal: === and !=== operators Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2014-07-12 08:33 +0000
csiph-web