Hello,
On Sun, 29 Nov 2020 11:36:45 +1100
Steven D'Aprano
On Sun, Nov 29, 2020 at 12:10:39AM +0300, Paul Sokolovsky wrote:
And we don't speak about some obscure "innovative" idea. Const'ness aka immutability is well-known and widely used feature in programming languages.
Constantness and immutability are not synonyms.
I agree. I'm just trying A/B testing to reach wider audience. I prefer the term (and keyword) "const", and the full term "constant variable". But if spelled like that, we immediately get nitpicks like "That doesn't sound well in colloquial English! Constant... variable? That's oxymoron!". These nitpicks miss that it's a term from a programming language domain, not a colloquial phrase. But we'll cover those nitpicks in detail elsewhere (in the python-ideas thread).
Immutability refers to *objects*. "abc" is an immutable object; `[]` is not, it is mutable.
Btw, nowadays "immutable variable" is also a pretty established term, thanks to a particular proglingo from some media company (forgot it's name (lingo's, not company's), something like fungus). []
Right, Python doesn't have that syntax. But it has other syntaxes to designate that a variable is defined in a particular scope:
# e is defined in the scope of the following block except Exception as e:
That is incorrect. e is defined in the *current* scope. There is no "scope of the following block".
Exception blocks are a special case, because there is dedicated code to unbind (delete) the "e" name when the block is left. But the name is local to the current scope, the block does not create a new scope.
It seems that I didn't convey my message well enough. What you render is "old way of thinking". The new way of thinking which I promote is: "'except as e' was an attempt to introduce block-level scoping, with truly subpar implementation details (like introducing block scope without real block scope)". []
*Could* define a, b in the scope of following block (and not beyond). That would have pros and cons, an obvious pro is that failing-to-match patterns would not litter in surrounding namespace, and con that "pattern matching as expression" usage would be more harder. If anything, use of block scoping could be considered to alleviate the littering problem
The "littering problem" will be a non-problem in practice.
"except as e" already confuses people: ----- e = 2.718281828 try: if random() < 0.1: 1/0 except Exception as e: print("Ha-ha! We're are not afraid of: %s" % e) # Bugreport: phase-of-moon dependent, my e is gone, gone!!11 print("In e we trust: %f" % e) ----- People already get confused by the "for" behavior, as the parallel thread on python-idea. With the bright future foretold for the pattern matching, you want to take a bet how many people will get confused by the poltergeist effect failed matches may have on the surrounding namespace? Well, I'd call that "cowboy attitude in programming language design" ;-).
Let's strive for solutions which follow the best practices in the programming language design (const'ness, block-level scoping are 2 good examples),
There isn't even a single definition for block-scoping. C block scoping and Java block scoping are not the same. So which one is best practice?
In theory, the best one is that of lambda calculus ;-). In practice, as you suggest, detail may vary by practical considerations. We'd certainly make it blend well with the rest of Python.
At *best* it is a matter of personal taste whether you like or dislike block scoping, but I'm going to stick my head out and say that it is an unnecessary complication that will cause more annoyance and confusion in Python than benefit.
That's useful opinion to hear, thanks. (But not the only one). The problem is that we already apply adhoc workarounds which already lead to annoyance and confusion. So you would need to compare amounts of existing annoyance with (predicted!) future annoyance for explicit block-scopes. My bet is that a well-proven technique, applied in a general fashion (but integrated well with the rest of language) would only alleviate levels of annoyance and confusion.
"Undefined behavior" regarding how failed matches may affect surrounding namespace is unlikely something to be proud of.
We should not use the term *undefined behaviour* because that carries too much baggage from C, where undefined behaviour is a truly frightening thing.
Me not useth, PEP634 doth: https://www.python.org/dev/peps/pep-0634/#side-effects-and-undefined-behavio...
In Python, it just means implementation defined.
In C it's the same. And you know the tales where it led it. (I'm personally still not afraid of it, but why purposefully establish it where it's not due?) []
Let us be clear: failed matches do not affect *surrounding* namespaces unless you declare capture variables as global or nonglobal. They *might* affect the current namespace, but not surrounding namespaces. Failed matches will not leak out to surrounding namespaces.
The problem is that intuitively (just like with "for"), "case a, b if a != b:" opens a new namespace for "a" and "b". That's why I talk about "surrounding namespace". Then if a particular case matching succeeds, weak of us (myself including) expect "a" and "b" to magically appear outside the "case" too. But if the case didn't match, nope, I don't expect "a" and "b" to appear there, it's not intuitive at all ;-).
-- Steve
[] -- Best regards, Paul mailto:pmiscml@gmail.com