repeated keyword arguments
the following code works on python 2.5:
def f(**kwargs): ... print kwargs ... f(a=5,b=7,a=8) {'a': 8, 'b': 7}
but fails on python2.4, saying that "a" is given twice. is this a bug or a feature? -tomer
Sounds like a regression in 2.5 (and in 2.6, and in 3.0). Probably due to the switch to the new AST-based compiler. Can you file a bug? I think we should leave 2.5 alone (too much risk of breaking code) but fix it in 2.6 and 3.0 if we can. --Guido On Fri, Jun 27, 2008 at 12:07 PM, tomer filiba <tomerfiliba@gmail.com> wrote:
the following code works on python 2.5:
def f(**kwargs): ... print kwargs ... f(a=5,b=7,a=8) {'a': 8, 'b': 7}
but fails on python2.4, saying that "a" is given twice. is this a bug or a feature?
-tomer
_______________________________________________ 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/guido%40python.org
-- --Guido van Rossum (home page: http://www.python.org/~guido/)
So we wait until they port their code to 2.6 to break it? regards Steve Guido van Rossum wrote:
Sounds like a regression in 2.5 (and in 2.6, and in 3.0). Probably due to the switch to the new AST-based compiler. Can you file a bug? I think we should leave 2.5 alone (too much risk of breaking code) but fix it in 2.6 and 3.0 if we can.
--Guido
On Fri, Jun 27, 2008 at 12:07 PM, tomer filiba <tomerfiliba@gmail.com> wrote:
the following code works on python 2.5:
def f(**kwargs): ... print kwargs ... f(a=5,b=7,a=8) {'a': 8, 'b': 7} but fails on python2.4, saying that "a" is given twice. is this a bug or a feature?
-tomer
_______________________________________________ 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/guido%40python.org
-- Steve Holden +1 571 484 6266 +1 800 494 3119 Holden Web LLC http://www.holdenweb.com/
Yes. On Fri, Jun 27, 2008 at 2:18 PM, Steve Holden <steve@holdenweb.com> wrote:
So we wait until they port their code to 2.6 to break it?
regards Steve
Guido van Rossum wrote:
Sounds like a regression in 2.5 (and in 2.6, and in 3.0). Probably due to the switch to the new AST-based compiler. Can you file a bug? I think we should leave 2.5 alone (too much risk of breaking code) but fix it in 2.6 and 3.0 if we can.
--Guido
On Fri, Jun 27, 2008 at 12:07 PM, tomer filiba <tomerfiliba@gmail.com> wrote:
the following code works on python 2.5:
def f(**kwargs):
... print kwargs ...
f(a=5,b=7,a=8)
{'a': 8, 'b': 7} but fails on python2.4, saying that "a" is given twice. is this a bug or a feature?
-tomer
_______________________________________________ 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/guido%40python.org
-- Steve Holden +1 571 484 6266 +1 800 494 3119 Holden Web LLC http://www.holdenweb.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/guido%40python.org
-- --Guido van Rossum (home page: http://www.python.org/~guido/)
On Fri, Jun 27, 2008 at 2:11 PM, Guido van Rossum <guido@python.org> wrote:
Sounds like a regression in 2.5 (and in 2.6, and in 3.0). Probably due to the switch to the new AST-based compiler. Can you file a bug? I think we should leave 2.5 alone (too much risk of breaking code) but fix it in 2.6 and 3.0 if we can.
I think code that uses this is probably already quite broken in some fundamental way and putting the fix in 2.5 isn't much of a risk. -- Cheers, Benjamin Peterson "There's no place like 127.0.0.1."
On 27-Jun-08, at 6:23 PM, Benjamin Peterson wrote:
On Fri, Jun 27, 2008 at 2:11 PM, Guido van Rossum <guido@python.org> wrote:
Sounds like a regression in 2.5 (and in 2.6, and in 3.0). Probably due to the switch to the new AST-based compiler. Can you file a bug? I think we should leave 2.5 alone (too much risk of breaking code) but fix it in 2.6 and 3.0 if we can.
I think code that uses this is probably already quite broken in some fundamental way and putting the fix in 2.5 isn't much of a risk.
I don't have 2.4 handy to test it, but it is more likely that a keyword and dictionary are passed, both containing the same item:
f(a=3, **{'a': 4})
Would that be a potential risk?
David Wolever wrote:
I don't have 2.4 handy to test it, but it is more likely that a keyword and dictionary are passed, both containing the same item:
f(a=3, **{'a': 4})
Would that be a potential risk?
Python 2.4.3
f(a=3, **{'a': 4}) Traceback (most recent call last): File "<stdin>", line 1, in ? TypeError: f() got multiple values for keyword argument 'a'
Python 2.5
f(a=3, **{'a': 4}) TypeError: f() got multiple values for keyword argument 'a'
The regression is purely in the way an argument list is reduced to a dictionary. -- Scott Dial scott@scottdial.com scodial@cs.indiana.edu
Scott Dial wrote:
The regression is purely in the way an argument list is reduced to a dictionary.
To further elaborate: Python 2.4:
import dis dis.dis(compile('f(a=3, b=1, a=4)', '', 'eval')) Traceback (most recent call last): File "<stdin>", line 1, in ? SyntaxError: duplicate keyword argument
Python 2.5:
import dis dis.dis(compile('f(a=3, b=1, a=4)', '', 'eval')) 1 0 LOAD_NAME 0 (f) 3 LOAD_CONST 0 ('a') 6 LOAD_CONST 1 (3) 9 LOAD_CONST 2 ('b') 12 LOAD_CONST 3 (1) 15 LOAD_CONST 0 ('a') 18 LOAD_CONST 4 (4) 21 CALL_FUNCTION 768 24 RETURN_VALUE
The old compiler checked for this, but the AST-based compiler just blindly compiles the entire keyword argument sequence. -Scott -- Scott Dial scott@scottdial.com scodial@cs.indiana.edu
On Fri, Jun 27, 2008 at 5:00 PM, Scott Dial <scott+python-dev@scottdial.com> wrote:
The old compiler checked for this, but the AST-based compiler just blindly compiles the entire keyword argument sequence.
The new compiler will check for it when my patch on the issue 3219 is applied. -- Cheers, Benjamin Peterson "There's no place like 127.0.0.1."
On Jun 27, 2008, at 5:23 PM, Benjamin Peterson wrote:
I think code that uses this is probably already quite broken in some fundamental way and putting the fix in 2.5 isn't much of a risk.
I suspect the risk has more to do with breaking something else in Python than in breaking 3rd-party code in this case. I think it should be fixed for 2.5 as well, myself. -Fred -- Fred Drake <fdrake at acm.org>
On Fri, Jun 27, 2008 at 2:54 PM, Fred Drake <fdrake@acm.org> wrote:
On Jun 27, 2008, at 5:23 PM, Benjamin Peterson wrote:
I think code that uses this is probably already quite broken in some fundamental way and putting the fix in 2.5 isn't much of a risk.
I suspect the risk has more to do with breaking something else in Python than in breaking 3rd-party code in this case.
I think it should be fixed for 2.5 as well, myself.
Let me clarify why I want to be so careful with this. If there is code that was expected to work but due to a bug in our code raises an exception, it's generally safe to fix this: people who ran into the issue found that their code didn't work, used a work-around, and that's the end of the story. But if there is code that was expected to *break* but due to a bug in our code *doesn't* raise an exception, people can very well have harmless occurrences of such code, and never noticed. Maybe their code is "broken" in the sense that it doesn't produce the correct result, but it may well be in a "don't care" way -- but if an upgrade suddenly starts raising the exception, they are likely to get unhandled exceptions where before they had none. This is particularly annoying when the author of the program that breaks is not the user of the program, to whose machine the upgrade was applied. In such cases I think it's better not to introduce new exceptions in point-point releases. -- --Guido van Rossum (home page: http://www.python.org/~guido/)
That's all fine and good but in this case there may be "stealth errors". If the user/programmer is expecting the first value to hold but instead On Fri, Jun 27, 2008 at 7:03 PM, Guido van Rossum <guido@python.org> wrote:
On Fri, Jun 27, 2008 at 2:54 PM, Fred Drake <fdrake@acm.org> wrote:
On Jun 27, 2008, at 5:23 PM, Benjamin Peterson wrote:
I think code that uses this is probably already quite broken in some fundamental way and putting the fix in 2.5 isn't much of a risk.
I suspect the risk has more to do with breaking something else in Python than in breaking 3rd-party code in this case.
I think it should be fixed for 2.5 as well, myself.
Let me clarify why I want to be so careful with this.
If there is code that was expected to work but due to a bug in our code raises an exception, it's generally safe to fix this: people who ran into the issue found that their code didn't work, used a work-around, and that's the end of the story.
But if there is code that was expected to *break* but due to a bug in our code *doesn't* raise an exception, people can very well have harmless occurrences of such code, and never noticed. Maybe their code is "broken" in the sense that it doesn't produce the correct result, but it may well be in a "don't care" way -- but if an upgrade suddenly starts raising the exception, they are likely to get unhandled exceptions where before they had none. This is particularly annoying when the author of the program that breaks is not the user of the program, to whose machine the upgrade was applied.
In such cases I think it's better not to introduce new exceptions in point-point releases.
-- --Guido van Rossum (home page: http://www.python.org/~guido/<http://www.python.org/%7Eguido/> ) _______________________________________________ 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/hall.jeff%40gmail.com
-- Haikus are easy Most make very little sense Refrigerator
oops... baby jumped in my lap... i pretty much said it all though... I think the error of the software functioning incorrectly may necessitate the patch... I certainly understand Guido's concern, however.
Guido van Rossum wrote:
In such cases I think it's better not to introduce new exceptions in point-point releases.
Perhaps they should be backported to the maintenance as warnings? Then users can decide on a case-by-case basis if they want to make that particularly warning trigger an exception. Cheers, Nick. -- Nick Coghlan | ncoghlan@gmail.com | Brisbane, Australia --------------------------------------------------------------- http://www.boredomandlaziness.org
Perhaps they should be backported to the maintenance as warnings? Then users can decide on a case-by-case basis if they want to make that particularly warning trigger an exception.
No. There will likely be one more 2.5 release. This entire issue never came up in the lifetime of 2.5, so it can't be so serious to annoy end-users with a warning they don't know how to deal with. Regards, Martin
On Fri, Jun 27, 2008 at 2:23 PM, Benjamin Peterson <musiccomposition@gmail.com> wrote:
On Fri, Jun 27, 2008 at 2:11 PM, Guido van Rossum <guido@python.org> wrote:
Sounds like a regression in 2.5 (and in 2.6, and in 3.0). Probably due to the switch to the new AST-based compiler. Can you file a bug? I think we should leave 2.5 alone (too much risk of breaking code) but fix it in 2.6 and 3.0 if we can.
I think code that uses this is probably already quite broken in some fundamental way and putting the fix in 2.5 isn't much of a risk.
No, it could just be a harmless typo in a long argument list. I really don't want to break code that is apparently working as part of an upgrade from 2.5.2 to 2.5.3. I want people to be completely fearless when it comes to such an upgrade: they should be able to just install it without having to think about testing anything, just like most people routinely install a new minor Linux upgrade pushed by their distribution. 2.6 is a different story, everyone knows they have to do testing before deciding it's safe to upgrade from 2.x to 2.(x+1). -- --Guido van Rossum (home page: http://www.python.org/~guido/)
On Jun 28, 12:56 am, "Guido van Rossum" <gu...@python.org> wrote:
No, it could just be a harmless typo in a long argument list.
to elaborate on this point a little, i came across this error when i ported my code to 2.4. i used the optparse class which takes 10's of kwargs, and it turned out i'd given the same parameter twice (the infamous copy-paste problem). so on the one hand, it was a harmless typo (because the latest instance was taken). on the other hand, it's a good thing i tested it on 2.4, or i'd never notice the repeated argument, which may have led to weird runtime errors (if the order of the params was changed). i'd be in favor of fixing this in 2.5, just to eliminate possibly hard- to-debug runtime errors. since it's a syntax error, it would be early- noticed when the code is first run/imported, and it wouldn't require the original author of the code to fix. -tomer
i'd be in favor of fixing this in 2.5, just to eliminate possibly hard- to-debug runtime errors. since it's a syntax error, it would be early- noticed when the code is first run/imported, and it wouldn't require the original author of the code to fix.
As release manager for Python 2.5, I'd like to support Guido's position: the risk of breaking existing code is just not worth it. Developers who made such a mistake will find out when they port the code to 2.6; there is no value whatsoever in end-users finding out minor bugs in software they didn't even know was written in Python. Regards, Martin
On Sat, Jun 28, 2008 at 1:30 AM, tomer filiba <tomerfiliba@gmail.com> wrote:
On Jun 28, 12:56 am, "Guido van Rossum" <gu...@python.org> wrote:
No, it could just be a harmless typo in a long argument list.
to elaborate on this point a little, i came across this error when i ported my code to 2.4. i used the optparse class which takes 10's of kwargs, and it turned out i'd given the same parameter twice (the infamous copy-paste problem).
so on the one hand, it was a harmless typo (because the latest instance was taken). on the other hand, it's a good thing i tested it on 2.4, or i'd never notice the repeated argument, which may have led to weird runtime errors (if the order of the params was changed).
i'd be in favor of fixing this in 2.5, just to eliminate possibly hard- to-debug runtime errors. since it's a syntax error, it would be early- noticed when the code is first run/imported, and it wouldn't require the original author of the code to fix.
But your anecdote is exactly why I don't want it fixed in 2.5. Your code was working, the typo was harmless. I don't want upgrades from 2.5.2 to 2.5.3 (or any x.y.z to x.y.(z+1)) to break code that was working before the upgrade! This is a principle we've adopted for such point-point upgrades for a long time. Also note that it took a long time before this was first reported, so it's not exactly like it's an important or frequent problem. -- --Guido van Rossum (home page: http://www.python.org/~guido/)
On Sat, 28 Jun 2008 11:17:10 am Greg Ewing wrote:
tomer filiba wrote:
def f(**kwargs):
... print kwargs ...
f(a=5,b=7,a=8)
{'a': 8, 'b': 7}
I can't think of any reason why one would need to be able to write such code, or even want to.
It would be nice to be able to do this: defaults = dict(a=5, b=7) f(**defaults, a=8) # override the value of a in defaults but unfortunately that gives a syntax error. Reversing the order would override the wrong value. So as Python exists now, no, it's not terribly useful. But it's not inherently a stupid idea. -- Steven
Steven D'Aprano wrote:
It would be nice to be able to do this:
defaults = dict(a=5, b=7) f(**defaults, a=8) # override the value of a in defaults
I can't help but think that would be difficult coding convention to use. However, I'm considerably less bothered by: def f_with_defaults(**kw): defaults = dict(a=5, b=7) defaults.update(kw) return f(**defaults) f_with_default(a=8) The only way f(**defaults, a=8) would be useful is if it happens a lot, and in that case, it's just as good of a candidate for being made into a function itself. I see this pattern all the time, and given that "f_with_defaults" probably has some semantic meaning, it probably would be nice to give it it's own name ("g"). Just my 2 cents. -- Scott Dial scott@scottdial.com scodial@cs.indiana.edu
"Steven D'Aprano" <steve@pearwood.info> wrote:
It would be nice to be able to do this:
defaults = dict(a=5, b=7) f(**defaults, a=8) # override the value of a in defaults
but unfortunately that gives a syntax error. Reversing the order would override the wrong value. So as Python exists now, no, it's not terribly useful. But it's not inherently a stupid idea.
There is already an easy way to do that using functools.partial, and it is documented and therefore presumably deliberate behaviour "If additional keyword arguments are supplied, they extend and override keywords."
from functools import partial def f(a=1, b=2, c=3): print a, b, c
g = partial(f, b=99) g() 1 99 3 g(a=100, b=101) 100 101 3
participants (13)
-
"Martin v. Löwis"
-
Benjamin Peterson
-
David Wolever
-
Duncan Booth
-
Fred Drake
-
Greg Ewing
-
Guido van Rossum
-
Jeff Hall
-
Nick Coghlan
-
Scott Dial
-
Steve Holden
-
Steven D'Aprano
-
tomer filiba