On Mon, Apr 20, 2020 at 5:04 AM Steven D'Aprano <steve@pearwood.info> wrote:
On Sun, Apr 19, 2020 at 06:06:50PM +0200, Alex Hall wrote:
> Sorry, what? How is there any doubt that the arguments being passed are
> dunder, invert, private, meta, and ignorecase? They're right there.

That tells us the meaning of the arguments in the *caller's* context.

[...] it is critical to
know the callee's context, i.e. the parameters those arguments get
bound to.

> Now, which parameters those arguments are bound to is less obvious, but:

Steven, what happened above? Immediately after your objection ends, you quoted me handling that objection. It feels like you're not reading what I say.
 
And the only way to know that is to think about the parameters. I trust
that you will agree that we should care about the difference between
(let's say):

    pow(8, 2)  # 64
    pow(2, 8)  # 256

and that it's critical to match the arguments to the parameters in the
right order or you will get the wrong answer.

I can't tell you how many times I messed up list.insert() calls because
I got the arguments in the wrong order.

None of your examples (delete_files, pow, list.insert) are relevant to the proposal. The hypothetical situation is that we have a call like:

function(**, dunder, invert, private, meta, ignorecase)

and a function definition:

def function(dunder, invert, private, meta, ignorecase): ...

My claim is that you'll probably quickly notice that the names are the same. Then you'll guess that they probably match up. Checking that the positions match seems a bit paranoid to me when you're reading someone else's 'complete' code - if they messed that up, they probably would have noticed.

Anyway, talking about this has made me feel not so convinced of my own argument. Especially if the list of parameters is long, it's hard to mentally do something like `set(argument_names) <= set(parameter_names)` as there's too many names to remember. You're more likely to do something like `for argument_name, parameter_name in zip(argument_names, parameter_names): assert argument_name == parameter_name` and then notice that something is suspiciously wrong.

So let's assume that a beginner is likely to notice arguments out of order and think that something is wrong, and focus on what happens from there. I think it's fair to say that the main concern is that they will have to look up and learn the syntax, and that is significant. But that (and anything else that happens during this time of initial confusion) is essentially an O(1) cost. The code and coders who use the syntax benefit from it for their lifetime, which is O(n).

Exactly what the benefits of the syntax are, I will have to leave that for another email...