One problem is that for else goes further, but not far enough. What if you want to do something if the loop _was_ broken out of? I've personally found that to be as common a case as doing something when the loop is done. What about do for loops? There's always something extra to add that would improve expressiveness in a few cases, but increase learning curve and decrease readability in all. There are plenty of other things we could do to modify the grammar and add "conveniences"...
case x:
// something
case y:
// something else
case z:
a = x
continue // reevaluate cases
}
But in any case, as with for else, they at most are only conveniences -- in this hypothetical switch continue case, you'd at most literally save one line of code (and it'd be backwards incompatible). In the for else case, you can always determine if the loop would have been broken out of by inverting the loop condition in a following if statement, taking effectively the same amount of code. If you need to determine that it was actually _not_ out of, it's 2 lines of code setup, plus 1 line per use of `break`, but in these cases, it's much easier to restructure code:
broken := true
for condition {
A()
if subcond1 {
B()
break
} else if subcond2 {
C()
break
}
} else {
// not broken out of
D()
broken := false
}
if !broken {
// common code for break cases
E()
F()
G()
}
// 19 lines of code for the above
for {
if !condition {
D()
break
}
A()
if subcond1 {
B()
goto commonbreak
} else if subcond2 {
C()
goto commonbreak
}
continue
commonbreak:
E()
F()
G()
break
}
// 20 lines of code for the above
broken := false
for !broken || condition {
A()
if subcond1 {
B()
broken = true
} else if subcond2 {
C()
broken = true
}
}
if broken {
E()
F()
G()
} else {
D() // the 'else' in 'for else' case
}
// 18 lines of code for the above
All 3 of the above are equivalent. The last two are valid Go right now, and for a common enough case (needing to know when it _is_ broken, as well as when not broken), the last one is clearer and shorter than the shortest "reasonable" for else case (you could make it shorter with `for broken := true; condition; {} else {}`, but that's just bad style.