-
Notifications
You must be signed in to change notification settings - Fork 1.1k
No outdent needed for else #10372
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
Should we add something like: Suggested by @kpbochenek |
Actually, that is already in the doc, I misunderstood. |
Sorry for the back and forth, but I spend a large amount of time trying to figure this condition out:
and it seems pretty unclear. We are inserting indents and outdents at tokenizer level and it's not really possible to distinguish between:
and
It also seems really hard to figure out what will happen in both scenarios. |
Here is first example:
On the other hand:
Here, the else follows the statement |
@odersky This is still a bit unclear. For example we have: val kind = if true then
println()
def hello =
println("Hello")
else println("B") Here
we should add:
which will add new level of complication, which we can deal with, but I am not sure what does it add to the language. Why not enforce: if cond then
statements...
else
statements... This would be similar as it's done in other indented based languages. I imagine this can cause a whole lot of confusion for people and no one will want to write it: if cond then
statements
else
statements |
I think the biggest problem with:
is that if someone inserts additional
then else will applied to 2nd |
I did not understand that.
So @romanowski Here's your example as a test: def statements = ???
def test(cond: Boolean) =
if cond then
if cond then
statements
else
statements Here's the test output with -Xprint:typer:
That looks correct to me, no?
|
I just meant it all at a tokenizer level, where we add indentation in Scalameta, that else follow a statement inside
This one does look correct, it's just the fact that adding an if inside a block changes the whole tree here. Overall, I feel that this is confusing for users, really hard to implement for us and I don't really understand why is it needed? I think it's very much related to #10671 in that we should be much more strict about indentation. |
I think the biggest difference between Scalameta and Dotty parser is that the first one tokenizes the input and then parses it, while the latter does it simultaneously. This allows to add the I am afraid that to support some of the cases we will need to rework the scalameta parser to be more similar to how Dotty parses the input. Though, I am not sure if that is possible. |
Would it be possible to use the Dotty parser instead? That's what I understand ammonite ended up doing. |
I should be able to rework the parser. Switching to dotty parser would be much more effort currently. Although, isn't this related to the other discussed issue about making the indentation stricter? Other indentation based languages expect 'else' to be on the same indentation level as 'if' from what I've seen. What is the purpose of making it possible to have it on the same indentation as the previous block? Honestly, it seems like a very specific use case and nothing I've seen people format their code like. Wouldn't it be simpler to just disallow it? In the dotty parser it requires a bit of a hack in a form of the observeOutdent method. |
Also, I've seen this used only once in the entire dotty codebase and I am pretty sure it's by mistake. |
I think we can make indentation stricter over time. But I am nervous about doing it now, since we make an implicit promise that reasonable Scala 2 code will continue to compile. And it's hard to predict 100% what's reasonable. I remember having seen quite a few unmotivated right-indents in code. The simple fact that I was forced to add the outdent trick shows that. I would not have done that if existing code compiled already OK without it. We could go back, remove outdent and see what breaks.But I'd prefer not to "tighten the screws" so late in the 3.0 cycle, since there might be a backlash. |
Ok I think I get where it's coming from. Are we are talking about a situation like: if (cond) {
statement()
} else {
statement()
} and that would be automatically rewritten by the compiler to: if (cond)
statement()
else
statement() ? If that is true I wonder if we shouldn't fix the rewrite rules to fix the indentation levels too? Or it should be something that scalafmt would actually do and not the automatic rewrite rules in the compiler?
Scala 2 should continue to compile as it will include braces I think. So if someone has a right indented I do understand the hesitation here, but this might take a bit longer for us to support it. Though, I think I have a plan on how to do it now. I will just hold off on implementing it until the syntax is 100 % set. |
No, this has nothing to do with indentation rewrites, they do the right thing. if cond then
statement()
else
statement() It has to do with the fact that indentation is significant everywhere, even inside braces. So we have to accept all existing code, unless the code is clearly misleading. So, this is misleading: if (x >= 0)
println(x)
1
else -1 whereas a shifted |
Why is this misleading? I mean it's a pretty clear if-else. if (x >= 0)
println(x)
1
else -1 This is much more misleading. What is an exact situation (code in Scala 2) that will not work if we remove the condition for |
Besides in Scala 2 we would need to write it: if (x >= 0){
println(x)
1
} else -1 To make it work. |
Also it seems the docs mention:
So this will not work: if x < 0 then
-x
-x
else
x but this will: if x < 0 then
-x
-x
else
x Why do we disallow that particular case, but not the other? This seems a bit inconsistent and is really hard to spot. |
I still find it a bit inconsistent, but fixed in scalameta parser scalameta/scalameta#2244 |
Minimized code
Output
This compiles.
Expectation
We expect an indentation after then, but in this case else should be an error. No outdent should be inserted before
else
.The text was updated successfully, but these errors were encountered: