News for hackers. Stuff that matters.
Re:Why Do Python Lists Multiply Oddly? Exploring the CPython... by Joker_vD on Tuesday April 09, 2024 @01:52AM (#39976497)
Well, those things are called "default argument values", not "default argument expressions", you know. It's a value that's reused for every function call, not an expression that re-evaluated at every function call.
Re:Why Do Python Lists Multiply Oddly? Exploring the CPython... by planede on Tuesday April 09, 2024 @04:12AM (#39977162)
I think calling it a default argument object would be much more clear. "Value" can still refer to an abstract, immutable concept, even the python docs use it like that at some places.
Re:Why Do Python Lists Multiply Oddly? Exploring the CPython... by chii on Tuesday April 09, 2024 @04:03AM (#39977122)
if you compare

> a = [0]

and

> b = [0]

these two expressions produces different 'value' objects for `[0]`, and modifying `a.append(a[-1] + 1)` does not change b.

so it's unintuitive that using `[0]` as a default value in a function argument can cause that argument to retain the same value across multiple function calls, when programmers would assume the argument to a function is not the same across multiple invocations.

The issue really here is the usage of an array object, which is not a value object (immutable), but a reference object. It would not have been a problem if the default argument was a string, or a number.

This is a reason not to use arrays in default arguments.

Re:Why Do Python Lists Multiply Oddly? Exploring the CPython... by Joker_vD on Tuesday April 09, 2024 @05:38AM (#39977730)
Very technically speaking, in "def f(a=[0]): ..." or in "a = [[0]] * 4" there is only one textual occurrence of "[0]", and the function definition is literally evaluated to define a function (you can try def "f(a=sys.stdout.write('Hi!')): return" in REPL to see when the default value gets constructed).

On the other hand, if we abstract from the technical minutiae, yes, it would have been entirely possible for Python to treat default arguments in the function definitions as expressions, by using machinery similar to what gets used for comprehensions: after all, as you point out, function's arguments (and local variables) do get re-assigned on every function call.

Re:Why Do Python Lists Multiply Oddly? Exploring the CPython... by throwaway0665 on Tuesday April 09, 2024 @01:58AM (#39976523)
Sure there is a reason it is that way. But it doesn't mean it's not incredibly unintuitive and error-prone.
Re:Why Do Python Lists Multiply Oddly? Exploring the CPython... by Joker_vD on Tuesday April 09, 2024 @02:03AM (#39976548)
Yes, the reason is that it's a tradition to have it this way. Python IMHO has decent enough assignment semantics that using "default argument expressions" model would've been fine, unlike e.g. in C++.
Re:Why Do Python Lists Multiply Oddly? Exploring the CPython... by kerkeslager on Tuesday April 09, 2024 @12:02PM (#39980846)
> Well, those things are called "default argument values", not "default argument expressions", you know.

No, I didn't know that, and I'd guess that the vast majority of Python developers don't, because people don't generally learn Python by reading the docs front to back and finding out the official names of everything.

> It's a value that's reused for every function call, not an expression that re-evaluated at every function call.

No one is confused about that. I'm aware that's how it is, but is that how it should be? I.e. if we could choose for this to be reused for every function call or re-evaluated every function call, which results in more intuitive behavior?