
On Thursday, January 28, 2016 11:51 AM, Jim J. Jewett <jimjjewett@gmail.com> wrote:
On Wed Jan 27 15:49:12 EST 2016, Andrew Barnert wrote:
both C# and Ruby made breaking changes from the Python behavior
...
The first few times I saw this, I figured Python had a stronger (and longer) backwards compatibility guarantee.
Ruby, sure, but C#, I don't think so. Most of the worst warts in C# 6.0 are there for backward compatibility.[1]
But now that I consider the actual breakage, I'm not so sure...
>>> for i in range(10): print (i) i=i+3 print(i)
i is explicitly changed, but it doesn't affect the flow control -- it gets reset to the next sequence item as if nothing had happened.
Yeah, that confusion is actually a separate issue. Explaining it in text is a bit difficult, but let's translate to the equivalent while loop: _it = iter(range(10)) try: while True: i = next(_it) print(i) i=i+3 print(i) except StopIteration: pass Now it should be obvious why you aren't affecting the control flow. And it should also be obvious why the "for let" change wouldn't make any difference here. Could Python solve that confusion? Sure. Swift, Scala, and lots of other languages make the loop variable constant/read-only/l-immutable/whatever, so that "i=i+3" either fails to compile, or raises at runtime, with a "ConstError". The idea is that "i=i=3" is more often a confusing bug than intentional--and, when it is intentional, the workaround is trivial (just write "j=i+3" and use j). But in dynamic languages, const tends to be more annoying than useful, so the smart ones (like Python) don't bother with it. [1] For example: Non-generic Task interferes with type inference for generic Task<T> much harder, and isn't used except by accident, but they added it anyway, in C# 5 in 2012, because it was needed for consistency with the non-generic collections, which have been deprecated since C# 2 in 2005 but can't be removed because some code might break.