Re: [Python-Dev] operator precedence of __eq__, __ne__, etc, if both object have implementations
This might help: http://mail.python.org/pipermail/python-dev/2008-June/080111.html Here is the most relevant part (quoting Guido): > Does it help if I tell you that for "x y" we always try > x.__binop__(y) before trying y.__reverse_binop__(x), *except* in the > case where y is an instance of a subclass of the class of x? jared On Sep 22, 2009, at 7:06 AM, Chris Withers wrote: Hi All, I didn't see any docs on this: http://docs.python.org/reference/datamodel.html?highlight=__eq__#object.__eq__ Where are the specifications on what happens if two objects are compared and both have implementations of __eq__? Which __eq__ is called? What happens if the first one called returns False? Is the second one called? What is one implements __eq__ and the other __ne__? If I've missed something, please point me in the right direction. To all those about to tell me to go read the source: that's not good enough here. I'm hoping there *are* "official" rules for how these interact and they just need better linking in, otherwise, I worry that IronPython could do one thing, Jython another and CPython a third... cheers, Chris -- Simplistix - Content Management, Batch Processing & Python Consulting - http://www.simplistix.co.uk ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/jflatow%40gmail.com ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
[Python-Dev] PySequence_Concat for dicts
Hi all, I am fairly new to the Python community so please forgive me (and correct me) if I am going about this wrong. I think it would be convenient and pythonic if dict objects implemented the PySequence_Concat method. I see there was once a short-lived discussion about this here: http://mail.python.org/pipermail/patches/2004-March/014323.html I have also been following the discussion about contributing to Python. It seems to me that this would be a fairly easy feature to implement (perhaps naively?), and I would be glad to try writing a patch for this if there is at least some chance of it making it into one of the branches. Can someone please advise me on what the correct order for going about this would be? Do I need to first write a PEP justifying why I think it would be an improvement? Which version of Python (if any), should a patch be targeted at? Otherwise, is there a good reason dicts do not already implement this method? I somewhat understand the complaint about commutativity, but as mentioned in the previous discussion, list concatenation is not commutative either. Seeing as update is the only builtin method for concatenation of dicts in the first place, it doesn't seem all that confusing that 'summing' two dicts should conveniently return a new instance that is the (only form of) concatenation of the two dicts. regards, jared ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] PySequence_Concat for dicts
On Jan 11, 2008, at 6:45 PM, Raymond Hettinger wrote: > IMO, the chainmap() recipe on ASPN is a much better solution since > it doesn't create a third dictionary with the all the attendant > allocation and copying effort. I wasn't suggesting that the result of concatenation would be a chained table, rather that it would perform the equivalent of an update and return the new dict (the same way extend works for lists). > It isn't a common use case to need to sum two dictionaries while > keeping both of the inputs unaltered. Inplace concatenation could be implemented more efficiently but would be exactly the same as calling update. jared ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] PySequence_Concat for dicts
> On Jan 11, 2008 5:21 PM, Raymond Hettinger <[EMAIL PROTECTED]> wrote: >> When does it come-up that you want a third summed dict >> while keeping the two originals around unchanged? Does >> it matter that the addition is non-commutative? Would >> a + b + c produce an intermediate a/b combo and then >> another new object for a/b/c so that the entries in >> a get copied twice and memory usage has to hold a, b, >> a/b, c, and a/b/c in memory all at the same time? There is no way around it, this will be less efficient than the inplace operation. If there were a precedent for calling a method like update and returning itself instead of None, I would suggest that, but since this is the way that has already been established for lists, it seems a natural extension. On Jan 11, 2008, at 9:22 PM, Guido van Rossum wrote: > It does suggest that we have two choices for the proposed operation: > d1+d2 or d1|d2. I think the latter may be more appropriate: > len(seq1+seq2) == len(seq1) ++len(seq2), but no such invariant exists > for set union. This might be way out there but I suppose you could consider that a dict is actually two different things, depending on what you are doing, and that these operations might actually do different things. Interpreted as a sequence, it is a sequence of key mappings. As confirmed in another recent discussion, Python guarantees consistent (read: repeatable) ordering of iteration through a dict, so in this sense it really is a sequence. (On a side note, I frequently rely on the repeatability of ordering when interacting with the Python shell). The notable sequence operation being + for concatenation, would perform an update of the keys (thus for the sequence op the mappings aren't guaranteed to be preserved, only the keys). The other interpretation of dict is obviously as a set of (key, value) pairs. For sets, the four major operations could behave exactly as any other set of (key, value) tuples (i.e. if you transform it to a list and then apply the same ops you should get the same result). jared p.s. If I were to get approval to implement some version of this, which version of Python would be appropriate to work with? ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] PySequence_Concat for dicts
On Jan 12, 2008, at 5:32 PM, Raymond Hettinger wrote: > Not natural, just inefficient and cute. Also, there was no answer > to the question about use cases. Fair enough. I will present some use cases below. > AFAICT, this feature has never been requested. The closest was a > feature request for a > variant of update() that avoided overwrites when a duplicate > key was encountered -- Guido rejected that one a long time ago. What about the patch I initially presented (and which you originally dealt with)? http://mail.python.org/pipermail/patches/2004-March/014323.html It seems the original request just never discussed the issue of duplicate keys (for some odd reason). > Your previous note suggests that there are alternative interpretations > of what the syntax could mean and that's not good a good thing. > That sort of ambiguity damages the language. It is not even > clear where the appropriate operators would be +-* or the > set operators &|^-. How about we keep sets for set operations and > dict for mapping operations and not foolishly conflate the two > just because we can. The mapping API is central to the language. > Altering it should be approached with a great deal of care. It was foolish of me to make those comments, you're right, and I should have known better. Guido has made it clear that the correct interpretation is that the keys of a dict form a set, which gets rid of any ambiguity. The set operators are most appropriate, though I am not exactly clear on whether this is already going to be implemented in a future version of Python, or if its just that noone will object if it appears in a future version. If it is the latter, I would still like to take a stab at implementing this as a first contribution. Would you please advise? > Also, the argument that we used + for lists so now we have > to do it for dicts is a weak one -- they are completely different > animals. > Operators are not the solution to all problems. In this case, we > don't even have a problem to be solved; there is just an urge > to hypergeneralize what was done for other datatypes where > it was appropriate. The .update() method we have now is explicit, > clear about its intent, and efficient. I agree operators are not the solution to all problems (need they be the solution to any?). My argument about + for lists was merely based on the precedent it established for sometimes sacrificing efficiency for clarity. Sometimes you may not want to alter the original lists (just as sometimes you may not want to alter the original dicts), but even when it does not matter if you do, you might still write: def prepend_with_a_b(list_a): return ['a', 'b'] + list_a instead of def prepend_with_a_b(list_a): list_b = ['a', 'b'] list_b.extend(list_a) return list_b Even though I suspect the latter will often be more efficient. The | operation for dict will not do anything that you could not otherwise do with update. I suspect most usage will be to simplify code as above. As for use cases when you actually want a new dict, I am guessing you do not want to know specifically why I don't want to alter dicts, but a more general use case, in which event the most generalized example is any case where you simply do not want to modify the original dicts. Since it seems that you might not actually need convincing that having the 4 set operations supported would be a reasonable thing to do, I will stop here for now. > IMO, the only thing this proposal has going for it is that it is cute. I suppose I should be glad for that? I might have thought you to put that to its discredit. Anyhow, I am not sure if we are now in agreement or not, but if so would you please advise on how to proceed? jared ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] trunc()
On Jan 25, 2008, at 1:22 PM, Raymond Hettinger wrote: > I wouldn't fret about this too much. Intrepreting int(f) as > meaning truncate has a *long* history in *many* programming > languages. It is a specious argument int(f) is ambiguous. > No one thinks it means ceil(f). Not that I think my opinion will have any weight in this discussion, but I'd agree that int has a long history not likely to be misinterpreted when applied to real numbers. Quoting from Graham, Knuth and Patashnik "Concrete Mathematics...2nd edition" page 67: "We start by covering the floor (greatest integer) and ceiling (least integer) functions, which are defined for all real x... ...some pocket calculators have an INT function, defined as floor(x) when x is positive and ceil(x) when x is negative. The designers of these calculators probably wanted their INT function to satisfy the identity INT(-X) = -INT(X). But we'll stick to our floor and ceiling functions, because they have even nicer properties than this." jared ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] Any Emacs tips for core developers?
On Feb 4, 2008, at 11:12 AM, [EMAIL PROTECTED] wrote: > Personally, I have been using GNU Emacs's new python mode since I > discovered it, and I've never encountered any of the bugs you just > described. (Perhaps you are describing bugs that arise from trying to > use it with XEmacs?) I'm not using XEmacs, but perhaps its Leopard-related. jared ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] Any Emacs tips for core developers?
I am not a core developer but I use emacs exclusively for development so you may find this useful. On Feb 3, 2008, at 6:53 PM, [EMAIL PROTECTED] wrote: > I am also the guy more-or-less responsible for syncing python-mode > with the > version delivered as part of the XEmacs packages (last synced about > a week > ago). The GNU Emacs folks wrote their own Python mode from scratch > a couple > years ago. Both are mentioned here: > >http://www.emacswiki.org/cgi-bin/wiki/PythonMode > > I have no experience with the GNU Emacs code. I recently upgraded to the emacs 22.1/python.el which I tried *really* hard to use, but eventually ended up installing python-mode again. There are a number of problems in the emacs lisp that I was able to get around, but eventually the bugginess overcame my will: *R, RE, and RET (i.e. the keystroke shift-r) were bound to commands in the major mode (meaning you couldn't type an R without triggering python-send-string). You can comment out this line in python.el to get around this: ;;(define-key map "\C-c\C-s" 'python-send-string) *echoing was occurring in the run-python shell. You can easily tell comint to process echoes for single-line commands, but if your tabs are converted to spaces you would need to do something like this to get rid of it in general: ;(add-hook 'inferior-python-mode-hook ; (lambda () ; (setq comint-process-echoes t) ; (set (make-variable-buffer-local 'indent-tabs-mode) nil))) * The emacs.py never worked for me (I ended up completely disabling it) * Opening a run-python shell when you already have one open does not work as you would expect. This is fixable also, but this was also the final straw for me. Realizing these things is very painful. Therefore I definitely recommend python-mode.el, which you can install by adding this to your .emacs: ;; Use a real man's python-mode (setq auto-mode-alist (cons '("\\.py$" . python-mode) auto-mode-alist)) (setq interpreter-mode-alist (cons '("python" . python-mode) interpreter-mode-alist)) (autoload 'python-mode "python-mode" "Python editing mode." t) (autoload 'py-shell "python-mode" "Python shell." t nil) Assuming the .el files are on your load-path and the .py files are in your site-packages. jared ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] Problems with the new super()
On May 1, 2008, at 9:21 PM, Greg Ewing wrote: If the classes being mixed clash or overlap in functionality somehow, the inheriting class needs to override all of the clashing methods and properties and resolve matters by delegating to one or another of the inherited classes (using explicit inherited method calls, not super!). Sorry but thats just not fair. It's not about convenience for the classes you're inheriting from, its so the inheriting class and superclasses can cooperate without requiring implementation details of one another. I agree that if your methods are 'clashing' then you are probably misinheriting, but cooperative methods can be the most natural way to model certain situations. Not to be dull but when building up a method from smaller reusable bits of functionality this is the case. Once you have explicitly stated the classes you want to inherit from, it isn't magic to expect some of their methods to chain without explicitly restating how exactly they should do that. In fact, doing so may make you more likely to make an error when you change which bits you want to include. If the method resolution order is there (and explicit somewhere) you might as well make use of it. If it's not feasible to do that for some reason, then you're better off forgetting about multiple inheritance and finding some other solution to the problem. Is it an issue of feasibility, or of what is the 'most obvious' solution? jared ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
[Python-Dev] Assumed reflexivity of rich comparison operators
Hi all, PEP 207 (http://www.python.org/dev/peps/pep-0207/) states in the fourth clause of the proposed resolutions to concerns: "The reflexivity rules *are* assumed by Python. Thus, the interpreter may swap y>x with x=x with x<=y, and may swap the arguments of x==y and x!=y." However, if this is the case, why does Python allow the definition of both pairs of __le__, __ge__ and __lt__, __gt__ for a single class, since users have no guarantee over which will be called? Currently, if I do not want x >= y to mean the same thing as y <= x (and believe it or not I believe I have a good use case for doing this), there is no reliable way of doing this. However, if the decision is to not allow users to do this at all using operators (and force them to create specially named methods), what is the point of allowing the definition of both? It seems very confusing to me (and indeed I was at first very confused what was going on), to tempt users to be able to define both but give no promise that if they do, the appropriate one will be called. Does anyone have a good explanation for this? Thanks! jared ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] Assumed reflexivity of rich comparison operators
On Jun 6, 2008, at 3:24 PM, Guido van Rossum wrote: On Fri, Jun 6, 2008 at 1:10 PM, Jared Flatow <[EMAIL PROTECTED]> wrote: PEP 207 (http://www.python.org/dev/peps/pep-0207/) states in the fourth clause of the proposed resolutions to concerns: "The reflexivity rules *are* assumed by Python. Thus, the interpreter may swap y>x with x=x with x<=y, and may swap the arguments of x==y and x!=y." However, if this is the case, why does Python allow the definition of both pairs of __le__, __ge__ and __lt__, __gt__ for a single class, since users have no guarantee over which will be called? Currently, if I do not want x = y to mean the same thing as y <= x (and believe it or not I believe I have a good use case for doing this), I find it hard to believe that your users will be happy with that though. :-) In this case, I am my users and I would be very happy with it (but I won't try to justify it :). there is no reliable way of doing this. Does it help if I tell you that for "x y" we always try x.__binop__(y) before trying y.__reverse_binop__(x), *except* in the case where y is an instance of a subclass of the class of x? Yes, actually that explains quite a bit, and now I see that is the case I am dealing with. y is an instance of a subclass of x, but the class of x is the one that defines both the binops. I suppose it is too much to ask to only call the __reverse_binop__ if the subclass overrides it. However, if the decision is to not allow users to do this at all using operators (and force them to create specially named methods), what is the point of allowing the definition of both? The same reason we allow (require) you to define __add__ and __radd_. It is quite possible that for any particular binary operation "x y", the class of x doesn't know how to implement it, and then the class of y is tried with the reversed operation. It seems very confusing to me (and indeed I was at first very confused what was going on), to tempt users to be able to define both but give no promise that if they do, the appropriate one will be called. Does anyone have a good explanation for this? I have explained it as well as I can. Thanks very much, at least that is enough information to work around reliably. jared ___ Python-Dev mailing list Python-Dev@python.org http://mail.python.org/mailman/listinfo/python-dev Unsubscribe: http://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com