ternary operator ?: suggestion

Dropping “case” might be interesting, since it becomes a little redundant in the “switch” situation, this is one advantage of having a new keyword, but not sure this reads as well:

let v = switch val then .Red: 1, .Green: 2, .Blue: 3

It is definitely nice in it’s compactness which is a big plus.

Another possibility, because “switch" does not need to resolve the syntactic ambiguity, but then we lose the “then” always meaning an expression consistency.

let v = switch val case .Red: 1, case .Green: 2, case .Blue: 3

this might be better for switch because we don’t need to mix “then” with “switch” which historically has not been done. Question is, is it better to go with “then” as expression consistency or with slightly more compact and following the conventions out there. Personally, I am not bothered by using “then” with “switch”

···

On Dec 12, 2015, at 4:03 AM, Al Skipp <al_skipp@fastmail.fm> wrote:

If at all possible, it’d be good to avoid adding new keywords, however if the keyword ‘then’ could enable 'if expressions’ and ‘switch expressions’, I’d be fully in favour.

Binding to a variable using a switch statement isn’t as elegant as it could be. The ability to define a ‘let’ variable and assigning a value later in a switch statement does help somewhat, but the examples below are very clear and elegant in my opinion. (I’d even question the necessity of the repetitive keyword ‘case’, but maybe that’s a step too far?)

Al

On 12 Dec 2015, at 07:15, Paul Ossenbruggen via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

So adding “then”:

let v = if condition then “A” else “B”

fixes that ambiguity and “then” would help differentiate an expression from a statement. I think there is value to having them separate constructs (for details see earlier comments in this thread). Also it is nice not having the braces in the expression.

Perhaps, similarly, “then" indicates an expression as opposed to a statement:

let v = switch condition then case Red: 1, case Blue: 2, case Green: 3

One downside is it, It may add confusion as to when to add the “then” clause as people will have to know what an expression vs statement is, but I suppose that is true with a ternary operator as well, and this reads better than a ternary operator. This also provides a good way to do single line switch expressions.

for multiline:

let v = if condition
  then “A”
  else “B"

let v = switch condition then
  case .Red: 1,
  case .Blue: 2,
  case .Green: 3

or with multiple expressions:

let v = switch condition then
  case .Red: 1,
  case .Blue: (if shade == .Dark then 4 else 2),
  case .Green: 3

On Dec 11, 2015, at 8:57 PM, Chris Lattner via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

On Dec 11, 2015, at 5:36 PM, Andrey Tarantsov via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

How about:

let v = if condition then “A" else “B"

I don't think introducing a separate "then" keyword is a good idea, two subtly different kinds of IFs would be confusing.

I guess you meant:

let v = if condition { "A" } else { "B” }

I don’t really want to wade into this discussion, but if A and B are intended to be *expressions* instead of an arbitrary sequence of statements|decls|exprs, then a more consistent syntax would be:

  let v = if condition (A) else (b)

The immediate problem with that is that juxtaposition of two expressions (condition, and A [with or without parens]) will lead to immediate syntactic ambiguity.

-Chris

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

I'm not quite sure how I feel about this specific proposal yet but in general I do want to see conditional expressions and removal of the ternary operator.

I would like to see "else if" included in whatever we adopt as the final solution. Is there a reason this is omitted from this proposal? I apologize if that was discussed in the thread. I haven't followed every post.

···

Sent from my iPad

On Dec 12, 2015, at 11:54 PM, Paul Ossenbruggen via swift-evolution <swift-evolution@swift.org> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and switch expressions based upon the discussions we had here. I have tried to keep the scope of the changes as small as possible, only added one keyword and kept things as similar to the existing language constructs as possible. If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

On Dec 12, 2015, at 3:51 PM, Paul Ossenbruggen <possen@gmail.com> wrote:

Implied in using the “then", if…then…else would aways require “else" when using “then” similar to how “guard" requires “else”. This will help to make the difference between statements and expressions clear.

let x = If cond then X else Y

is the full form, where “else" can not be omitted.

On Dec 12, 2015, at 12:59 PM, Paul Ossenbruggen <possen@gmail.com> wrote:

On Dec 12, 2015, at 12:37 PM, Andrey Tarantsov via swift-evolution <swift-evolution@swift.org> wrote:

1. I would really hate to explain to someone when if needs a then and when it doesn't. That's the sort of inconsistency that shouldn't be added lightly.

agreed definitely want to be careful with that. I think with braces meaning statements that differentiation can be made clear. I would certainly start with statements when describing, just as you usually don’t talk about the ternary operator until later.

3. If we can somehow solve all of this, I think I'll be +1 for replacing (A ? B : C) with some sort of (if A then B else C).

Yes that would be great.

4. Generally, I wonder how hard would it be for all statements to be usable as expressions? Why didn't Swift go that way from the start?

The biggest problem statement is you don’t need to exhaustively specify every outcome:

if cond {
  print(“hello”)
}

whereas in an expression you have to specify what happens in the else.

let say = if cond then “hello” else “goodbye"

unless you go seriously off the deep end:

let say = if cond then “hello”

“say" then becomes an optional, *shudder*

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and switch expressions based upon the discussions we had here. I have tried to keep the scope of the changes as small as possible, only added one keyword and kept things as similar to the existing language constructs as possible. If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

Thanks for taking the time to put this detailed proposal together.

Regarding the if…then…else expression, it all looks good to me.
I have a few comments on the proposed switch expression:

1)
Is it worth reusing the ‘then’ keyword, instead of colon? If a new keyword is to be added, it’d be good if it wasn’t restricted to only one use. The advantage of using ‘then’ in switch would be to further distinguish the expression from the statement and would fit with the if…then…else expression. The disadvantage is that it adds a little more verbosity (ideally, expressions should be syntactically light-weight).

I was doing my best to stay with with the existing model for switch if possible so using the existing constructs both make the implementation simpler and hopefully consistent with the way switch currently works. The main change here is that each part is an expression instead of statement(s) otherwise it is the same old switch but usable where you would have expressions.

2)
Having the ‘case’ keyword appear only once, looks a bit odd to me, it gives the impression that it is only associated with the first case.
My preference would be to omit the ‘case’ keyword entirely. In the switch statement it can be helpful, as the cases can run over several lines, therefore the keyword is a handy visual marker for the different cases. The expression for each case should only be one line, so this visual marker shouldn’t be required for switch expressions. Having said that, I understand if people think this is too much of a change. Therefore my suggestion is, either the ‘case’ keyword is omitted from the expression, or it is associated with every case as it currently is with the switch statement.

I explored adding “cases” which could be interchanged with “case” but decided against it because it would add another keyword. Also, the idea was to have this work the same as the switch statement. Currently switch statements allow you to have a single word “case” followed by multiple comma separated cases. Since case and cases would just behave the same, I am not opposed to adding back in if there is significant benefit in readability.

3)
It might be worth showing an example of binding to associated values in a enum using a switch expression? However, the behaviour should be identical to the switch statement, so this might not be required.

Ok will add that.

···

On Dec 13, 2015, at 3:59 AM, Al Skipp <al_skipp@fastmail.fm> wrote:

On 13 Dec 2015, at 05:54, Paul Ossenbruggen via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Al

I see that this will help with consistency, this would address the question of when to use “then". I would not want to require it on statements. I like how you can simply put the brace after then condition in the existing Swift. It would be required for expression but not for statements. I can add this change if others like it too.

···

On Dec 13, 2015, at 6:39 AM, Thorsten Seitz <tseitz42@icloud.com> wrote:

Hi Paul,

thanks for gathering the ideas in a proposal!

You suggested to use if…then…else instead of just using the statement form if … {…} else {…}.
In that case I wonder whether it wouldn’t be better to use „then“ in if-statements as well for consistency:

if condition then {
  …
} else {
  …
}

For switch-expressions I’d just keep the statement syntax as there is only one pair of braces and not one per case. Separating the expressions, for which „then“ had to be introduced in case of the if-expression, is already done nicely by the „case“ keywords.
Here, too, my intent would be to keep the syntax of expression and statement the same for consistency.

Some remarks on the section about alternatives:

The problem with this is that in expressions all cases must be handled. In a statement it is common to not have else. So you could make it an expression if the return value is used. This makes it more complex from both the user's perspective and the compiler perspective. That means that if you were to change a "if" conditional into an expression suddenly you would get an an error if the "else" part was not provided.

I don’t see any problem here. The only rule is that expressions have to have an else clause. This is independent of syntax i.e. whether we uses braces or „then".

Especially for the switch expression I don’t think the standard statement syntax with braces looks bad (as there is only one pair of braces around all cases and not one per case like in the if-statement), at least if you format it a little bit different than in your proposal and drop the unnecessary parentheses:

let color =
    switch enumColor {
    case .Red:
        switch shade {
        case .DarkRed: 0xFFEEEE
        case .LightRed: 0xFF0000
        default: 0xFF1010
        }
    default: 0xFFFFFF
    }

-Thorsten

Am 13.12.2015 um 06:54 schrieb Paul Ossenbruggen via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>>:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and switch expressions based upon the discussions we had here. I have tried to keep the scope of the changes as small as possible, only added one keyword and kept things as similar to the existing language constructs as possible. If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

On Dec 12, 2015, at 3:51 PM, Paul Ossenbruggen <possen@gmail.com <mailto:possen@gmail.com>> wrote:

Implied in using the “then", if…then…else would aways require “else" when using “then” similar to how “guard" requires “else”. This will help to make the difference between statements and expressions clear.

let x = If cond then X else Y

is the full form, where “else" can not be omitted.

On Dec 12, 2015, at 12:59 PM, Paul Ossenbruggen <possen@gmail.com <mailto:possen@gmail.com>> wrote:

On Dec 12, 2015, at 12:37 PM, Andrey Tarantsov via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

1. I would really hate to explain to someone when if needs a then and when it doesn't. That's the sort of inconsistency that shouldn't be added lightly.

agreed definitely want to be careful with that. I think with braces meaning statements that differentiation can be made clear. I would certainly start with statements when describing, just as you usually don’t talk about the ternary operator until later.

3. If we can somehow solve all of this, I think I'll be +1 for replacing (A ? B : C) with some sort of (if A then B else C).

Yes that would be great.

4. Generally, I wonder how hard would it be for all statements to be usable as expressions? Why didn't Swift go that way from the start?

The biggest problem statement is you don’t need to exhaustively specify every outcome:

if cond {
  print(“hello”)
}

whereas in an expression you have to specify what happens in the else.

let say = if cond then “hello” else “goodbye"

unless you go seriously off the deep end:

let say = if cond then “hello”

“say" then becomes an optional, *shudder*

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

Good point, maybe breaking it up makes sense.

···

On Dec 13, 2015, at 8:05 AM, J. Cheyo Jimenez <cheyo@masters3d.com> wrote:

This is great. Here is my take on it.

Should these be two proposals? One for the if-then-else expression and one for the switch expression?
I think the proposal would have a better chance if it is focused first on replacing ?: with if-then-else. It is a very emotional change for a lot of people. At the end of the proposal you could just briefly mention the switch expression possibility (I like Al's suggestions.)

If the if then else expression gets approved and implemented then it would be easier to get a switch expression using the then keyword imo but I do think we need to include it in the proposal but as a future implementation and/or possibility.

On Saturday, December 12, 2015, Paul Ossenbruggen via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and switch expressions based upon the discussions we had here. I have tried to keep the scope of the changes as small as possible, only added one keyword and kept things as similar to the existing language constructs as possible. If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

On Dec 12, 2015, at 3:51 PM, Paul Ossenbruggen <possen@gmail.com <javascript:_e(%7B%7D,'cvml','possen@gmail.com');>> wrote:

Implied in using the “then", if…then…else would aways require “else" when using “then” similar to how “guard" requires “else”. This will help to make the difference between statements and expressions clear.

let x = If cond then X else Y

is the full form, where “else" can not be omitted.

On Dec 12, 2015, at 12:59 PM, Paul Ossenbruggen <possen@gmail.com <javascript:_e(%7B%7D,'cvml','possen@gmail.com');>> wrote:

On Dec 12, 2015, at 12:37 PM, Andrey Tarantsov via swift-evolution <swift-evolution@swift.org <javascript:_e(%7B%7D,'cvml','swift-evolution@swift.org');>> wrote:

1. I would really hate to explain to someone when if needs a then and when it doesn't. That's the sort of inconsistency that shouldn't be added lightly.

agreed definitely want to be careful with that. I think with braces meaning statements that differentiation can be made clear. I would certainly start with statements when describing, just as you usually don’t talk about the ternary operator until later.

3. If we can somehow solve all of this, I think I'll be +1 for replacing (A ? B : C) with some sort of (if A then B else C).

Yes that would be great.

4. Generally, I wonder how hard would it be for all statements to be usable as expressions? Why didn't Swift go that way from the start?

The biggest problem statement is you don’t need to exhaustively specify every outcome:

if cond {
  print(“hello”)
}

whereas in an expression you have to specify what happens in the else.

let say = if cond then “hello” else “goodbye"

unless you go seriously off the deep end:

let say = if cond then “hello”

“say" then becomes an optional, *shudder*

+1 on this.

"This is also why I think I expressions and statements should be different.
Trying to make statements into expressions will lead to a lot of
complications and will lead to harder to understand programming model. Not
saying it is impossible but definitely much more involved. "

···

On Sunday, December 13, 2015, Paul Ossenbruggen via swift-evolution < swift-evolution@swift.org> wrote:

Hi Taras,

I understand your point, if you need to do what you are suggesting, which
is multiple statements which, eventually resolve to one result, You would
still be able to do that with the existent switch statement. The expression
syntax should be thought of as more functional in that you don’t have side
effects and other processing in it. It simply flows through and produces
one answer as any other expression would.

Another way to think of it, is if you think you should be able to do it
with a ternary operator, then you should be able to do it with the proposed
solution.

On Dec 13, 2015, at 6:53 AM, Taras Zakharko <taras.zakharko@googlemail.com > <javascript:_e(%7B%7D,'cvml','taras.zakharko@googlemail.com');>> wrote:

Hi Paul,

what bothers me in your proposal is that you seem to allow only simple
expressions. But it is often the case that one needs to have multiple
statements to set up the value. For example:

  let data = if connection.valid
    connection.cached_data
  else {
    // generate the data again
}

I have been thinking a bit about how to implement this in connection with
the idea of code blocks as closures proposal I have posted earlier (
https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20151207/002056.html\).
Switch is a bit more complicated, but I think that the existing if
statement can be easily turned into expression:

   func if_<T>(condition: Bool, then_: (()->T)?, else_: (()->T)?) -> T? {
    var result: T?

    if condition {
        result = then_?()
    } else {
        result = else_?()
    }

    return result
}

the compiler would then translate all if statements into

   if_(condition, then_: then block, else_: else block)

Your if_ func is interesting, I am going play with this a bit.

if the else block is not present, it will be set to nil. In that case the
if expression also evaluates to nil. Now, if the if is used as a statement,
the above transformation is sufficient and the return value will be
optimised away by the compiler. If the expression form is used (i.e. there
is an assignment operation), the compiler will forcefully unwrap the result:

Unless I am misunderstanding your suggestion, I experimented with leaving
“else” off resulting in an optional if not all cases are handled. This I
think makes it confusing because now you have to deal with an optional,
optionals usually mean more conditionals later. I want to know at the end
of the expression that my variable was properly set in all cases. It seems
like trouble to deal with the possibility that you don’t know the result of
the expression at the end of the expression, which is essentially what you
have with the nil result and everything after that has to deal with that
optional. Doesn’t that mean that all if expressions would return some sort
of optional?

let x = if_(condition, then_: then block, else_: else block)!

This way, if else block is absent, the program will crash. A bit of
tweaking will also generate a useful error message. I am also sure that it
is possible to generate a warning (or even an error) at the compile time
without too much effort.

It would be preferred to not have runtime errors or compiler errors to
deal with. My proposal, by guaranteeing a result, would not have that
issue. This is also why I think I expressions and statements should be
different. Trying to make statements into expressions will lead to a lot of
complications and will lead to harder to understand programming model. Not
saying it is impossible but definitely much more involved.

I think the nice thing about this proposal is that it uses already
existing mechanisms in the language and only requires some minimal
transformations by the compiler.

The switch expression can be approached in a similar way, but would
require more compiler magic.

Best,

Taras

On 13 Dec 2015, at 06:54, Paul Ossenbruggen via swift-evolution < > swift-evolution@swift.org > <javascript:_e(%7B%7D,'cvml','swift-evolution@swift.org');>> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and
switch expressions based upon the discussions we had here. I have tried to
keep the scope of the changes as small as possible, only added one keyword
and kept things as similar to the existing language constructs as possible.
If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

On Dec 12, 2015, at 3:51 PM, Paul Ossenbruggen <possen@gmail.com > <javascript:_e(%7B%7D,'cvml','possen@gmail.com');>> wrote:

Implied in using the “then", if…then…else would aways require “else" when
using “then” similar to how “guard" requires “else”. This will help to
make the difference between statements and expressions clear.

let x = If cond then X else Y

is the full form, where “else" can not be omitted.

On Dec 12, 2015, at 12:59 PM, Paul Ossenbruggen <possen@gmail.com > <javascript:_e(%7B%7D,'cvml','possen@gmail.com');>> wrote:

On Dec 12, 2015, at 12:37 PM, Andrey Tarantsov via swift-evolution < > swift-evolution@swift.org > <javascript:_e(%7B%7D,'cvml','swift-evolution@swift.org');>> wrote:

1. I would really hate to explain to someone when *if* needs a *then* and
when it doesn't. That's the sort of inconsistency that shouldn't be added
lightly.

agreed definitely want to be careful with that. I think with braces
meaning statements that differentiation can be made clear. I would
certainly start with statements when describing, just as you usually don’t
talk about the ternary operator until later.

3. If we can somehow solve all of this, I think I'll be +1 for replacing
(A ? B : C) with some sort of (*if* A *then* B *else* C).

Yes that would be great.

4. Generally, I wonder how hard would it be for all statements to be
usable as expressions? Why didn't Swift go that way from the start?

The biggest problem statement is you don’t need to exhaustively specify
every outcome:

if cond {
print(“hello”)
}

whereas in an expression you have to specify what happens in the else.

let say = if cond then “hello” else “goodbye"

unless you go seriously off the deep end:

let say = if cond then “hello”

“say" then becomes an optional, *shudder*

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
<javascript:_e(%7B%7D,'cvml','swift-evolution@swift.org');>
https://lists.swift.org/mailman/listinfo/swift-evolution

I really don't like the "if cond then expr1 else expr2".

1) First of all, it's extremely verbose. It's almost as bad as the SQL construct "case when cond then expr1 else expr2 end”.

Yeah it adds a few characters overall. What used to be 2 chars now takes 10. Clarity is preferred though by many. I head frequently people telling users to never use ternary operators because they are confusing to read.

2) It makes Swift harder to learn. Newcomers will be confused why you sometimes need to use curly braces and why at other times you need to use the "then" keyword.

I did mention this in Alternatives Considered section. By making the else part required, this emphasizes that it is different or we could go with an optional “then” for statements as was suggested by Thorsten.

3) It doesn't help when you want to do multi-line calculations

This is the case with the ternary as well, I think it is better to keep it simple.

But there is one good side to this proposal: it nests more naturally than the ternary operator:
"if cond then expr1 else if cond2 then expr2 else expr3"
vs.
"cond ? expr1 : (cond2 ? expr2 : expr3)

The proposed syntax for the switch statement is so confusing that I really don't think it is a good idea.

Not sure why that is, it is essentially the same as the existing switch statement except everything is an expression instead of statements. Is there anything I can do in the examples or documentation to make things clearer?

Why not just allow normal if statements to return values?
I don't see what's so bad about the following:
"let value = if cond {expr1} else {expr2}"

This would also extend to multiple lines:
let value = if cond {
  expr1
} else {
  let something = Object()
  something.doStuff()
  something
}

I answered this with others, also notice how there are braces everywhere? does that really work when you just want to put something on one line. What happens when one of your branches returns void? Expressions are guaranteed to have a result, statements don’t make such a guarantee.

···

On Dec 13, 2015, at 8:11 AM, Jakob Egger <jakob@eggerapps.at> wrote:

Jakob

On 13 Dec 2015, at 06:54, Paul Ossenbruggen via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and switch expressions based upon the discussions we had here. I have tried to keep the scope of the changes as small as possible, only added one keyword and kept things as similar to the existing language constructs as possible. If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

Using fully-fledged if/switch-statements as expressions is another proposal
and discussion (which already exists).

The replacement of the ternary operator should be just syntactic sugar for
the other proposal to have a shorter version of "let x = if a {} else {}".

Regarding the "then" keyword:
What about "do"?

let x = if a do b else c

Yes, it reads a bit weird, but as if & switch statements are moving towards
being expressions already then "do" blocks will likely too.

So the above example would just be another shortcut for

let x = if a { do { b } } else { c }

···

On Sun, Dec 13, 2015 at 3:56 PM, Taras Zakharko via swift-evolution < swift-evolution@swift.org> wrote:

Hi Paul,

what bothers me in your proposal is that you seem to allow only simple
expressions. But it is often the case that one needs to have multiple
statements to set up the value. For example:

  let data = if connection.valid
    connection.cached_data
  else {
    // generate the data again
}

I have been thinking a bit about how to implement this in connection with
the idea of code blocks as closures proposal I have posted earlier (
https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20151207/002056.html\).
Switch is a bit more complicated, but I think that the existing if
statement can be easily turned into expression:

   func if_<T>(condition: Bool, then_: (()->T)?, else_: (()->T)?) -> T? {
    var result: T?

    if condition {
        result = then_?()
    } else {
        result = else_?()
    }

    return result
}

the compiler would then translate all if statements into

   if_(condition, then_: then block, else_: else block)

if the else block is not present, it will be set to nil. In that case the
if expression also evaluates to nil. Now, if the if is used as a statement,
the above transformation is sufficient and the return value will be
optimised away by the compiler. If the expression form is used (i.e. there
is an assignment operation), the compiler will forcefully unwrap the result:

let x = if_(condition, then_: then block, else_: else block)!

This way, if else block is absent, the program will crash. A bit of
tweaking will also generate a useful error message. I am also sure that it
is possible to generate a warning (or even an error) at the compile time
without too much effort.

I think the nice thing about this proposal is that it uses already
existing mechanisms in the language and only requires some minimal
transformations by the compiler.

The switch expression can be approached in a similar way, but would
require more compiler magic.

Best,

Taras

On 13 Dec 2015, at 06:54, Paul Ossenbruggen via swift-evolution < > swift-evolution@swift.org> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and
switch expressions based upon the discussions we had here. I have tried to
keep the scope of the changes as small as possible, only added one keyword
and kept things as similar to the existing language constructs as possible.
If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

On Dec 12, 2015, at 3:51 PM, Paul Ossenbruggen <possen@gmail.com> wrote:

Implied in using the “then", if…then…else would aways require “else" when
using “then” similar to how “guard" requires “else”. This will help to
make the difference between statements and expressions clear.

let x = If cond then X else Y

is the full form, where “else" can not be omitted.

On Dec 12, 2015, at 12:59 PM, Paul Ossenbruggen <possen@gmail.com> wrote:

On Dec 12, 2015, at 12:37 PM, Andrey Tarantsov via swift-evolution < > swift-evolution@swift.org> wrote:

1. I would really hate to explain to someone when *if* needs a *then* and
when it doesn't. That's the sort of inconsistency that shouldn't be added
lightly.

agreed definitely want to be careful with that. I think with braces
meaning statements that differentiation can be made clear. I would
certainly start with statements when describing, just as you usually don’t
talk about the ternary operator until later.

3. If we can somehow solve all of this, I think I'll be +1 for replacing
(A ? B : C) with some sort of (*if* A *then* B *else* C).

Yes that would be great.

4. Generally, I wonder how hard would it be for all statements to be
usable as expressions? Why didn't Swift go that way from the start?

The biggest problem statement is you don’t need to exhaustively specify
every outcome:

if cond {
print(“hello”)
}

whereas in an expression you have to specify what happens in the else.

let say = if cond then “hello” else “goodbye"

unless you go seriously off the deep end:

let say = if cond then “hello”

“say" then becomes an optional, *shudder*

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

Why not just allow normal if statements to return values?
I don't see what's so bad about the following:
"let value = if cond {expr1} else {expr2}"

I’d be happy if the ‘if’ and ‘switch’ statements could somehow also behave as expressions. One problem is that an ‘if’ statement doesn’t require an ‘else’ clause, whereas an expression does.

Taras, earlier mentioned a possible solution, which would return ‘nil’ if the else clause was absent. I think any suggestion must have compile time checking to prevent runtime crashes occurring.

This would also extend to multiple lines:
let value = if cond {
  expr1
} else {
  let something = Object()
  something.doStuff()
  something
}

My personal preference here is that ‘if’ expressions should aim to fit onto one line and avoid invoking side-effecting functions. However, Swift isn’t a language which controls side-effects within the type system, so maybe my point is moot?

···

On 13 Dec 2015, at 16:11, Jakob Egger via swift-evolution <swift-evolution@swift.org> wrote:

I would start it independently and put a note somewhere that in case
if/switch/do become expressions on their own then your proposal will
automatically turn into a simplified syntax for them.

···

On Sun, Dec 13, 2015 at 5:05 PM, J. Cheyo Jimenez via swift-evolution < swift-evolution@swift.org> wrote:

This is great. Here is my take on it.

Should these be two proposals? One for the if-then-else expression and one
for the switch expression?
I think the proposal would have a better chance if it is focused first on
replacing ?: with if-then-else. It is a very emotional change for a lot of
people. At the end of the proposal you could just briefly mention the
switch expression possibility (I like Al's suggestions.)

If the if then else expression gets approved and implemented then it would
be easier to get a switch expression using the then keyword imo but I do
think we need to include it in the proposal but as a future implementation
and/or possibility.

On Saturday, December 12, 2015, Paul Ossenbruggen via swift-evolution < > swift-evolution@swift.org> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and
switch expressions based upon the discussions we had here. I have tried to
keep the scope of the changes as small as possible, only added one keyword
and kept things as similar to the existing language constructs as possible.
If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

On Dec 12, 2015, at 3:51 PM, Paul Ossenbruggen <possen@gmail.com> wrote:

Implied in using the “then", if…then…else would aways require “else"
when using “then” similar to how “guard" requires “else”. This will help
to make the difference between statements and expressions clear.

let x = If cond then X else Y

is the full form, where “else" can not be omitted.

On Dec 12, 2015, at 12:59 PM, Paul Ossenbruggen <possen@gmail.com> wrote:

On Dec 12, 2015, at 12:37 PM, Andrey Tarantsov via swift-evolution < >> swift-evolution@swift.org> wrote:

1. I would really hate to explain to someone when *if* needs a *then*
and when it doesn't. That's the sort of inconsistency that shouldn't be
added lightly.

agreed definitely want to be careful with that. I think with braces
meaning statements that differentiation can be made clear. I would
certainly start with statements when describing, just as you usually don’t
talk about the ternary operator until later.

3. If we can somehow solve all of this, I think I'll be +1 for replacing
(A ? B : C) with some sort of (*if* A *then* B *else* C).

Yes that would be great.

4. Generally, I wonder how hard would it be for all statements to be
usable as expressions? Why didn't Swift go that way from the start?

The biggest problem statement is you don’t need to exhaustively specify
every outcome:

if cond {
print(“hello”)
}

whereas in an expression you have to specify what happens in the else.

let say = if cond then “hello” else “goodbye"

unless you go seriously off the deep end:

let say = if cond then “hello”

“say" then becomes an optional, *shudder*

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

I must say I agree with Jakob. Adding a ternary expression if variant only makes the language more complex (in every sense of this word) and does not really solve anything. A general ‘if-as-expression’ is a more ‘sustainable’ solution and more inline with Swift3 spirit of simplification.

Best,

Taras

···

On 13 Dec 2015, at 17:11, Jakob Egger via swift-evolution <swift-evolution@swift.org> wrote:

I really don't like the "if cond then expr1 else expr2".

1) First of all, it's extremely verbose. It's almost as bad as the SQL construct "case when cond then expr1 else expr2 end".

2) It makes Swift harder to learn. Newcomers will be confused why you sometimes need to use curly braces and why at other times you need to use the "then" keyword.

3) It doesn't help when you want to do multi-line calculations

But there is one good side to this proposal: it nests more naturally than the ternary operator:
"if cond then expr1 else if cond2 then expr2 else expr3"
vs.
"cond ? expr1 : (cond2 ? expr2 : expr3)

The proposed syntax for the switch statement is so confusing that I really don't think it is a good idea.

Why not just allow normal if statements to return values?
I don't see what's so bad about the following:
"let value = if cond {expr1} else {expr2}"

This would also extend to multiple lines:
let value = if cond {
  expr1
} else {
  let something = Object()
  something.doStuff()
  something
}

Jakob

On 13 Dec 2015, at 06:54, Paul Ossenbruggen via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and switch expressions based upon the discussions we had here. I have tried to keep the scope of the changes as small as possible, only added one keyword and kept things as similar to the existing language constructs as possible. If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

I don't see the "improved" clarity.

Without syntax highlighting, and no indentation to help, it becomes impossible to read. Compare:

let x = if cond then expr1 else expr2
vs
let x = cond ? expr1 : expr2

With syntax highlighting, it is eminently readable.

The use of ‘?’ is also associated with Optionals in Swift, other languages don’t have this association. The ‘:’ symbol has multiple uses already; separate declarations from types, separate keys and values in Dictionaries, indicates inheritance and protocol conformance…

The former looks just like a random English sentence, the latter is obviously a ternary expression (to my trained eye)

The ternary operator exists in very many languages, and therefore many programmers are familiar with them.

If the purpose is to make the language easier to understand for novice programmers, maybe you could use "when" instead of "if", for example:

let x = when cond then expr1 else expr2

This has several advantages:

1) The difference between statements and expressions becomes trivial:
- "if" is a statement
- "when" is an expression

2) it becomes easier to google. "swift when" might get better results compared to "swift ?" or "swift if"

3) people familiar with SQL will recognise the functional WHEN expression

4) Of course it is even longer, but at this point, who cares.

To add one key word to the language to support ‘if’ expressions may be regarded as a misfortune; to add two looks like carelessness. (apologies to Oscar Wilde : )

···

On 14 Dec 2015, at 08:49, Jakob Egger via swift-evolution <swift-evolution@swift.org> wrote:

Without commenting on anything else in this thread, ?: nests properly (right-associative-ly) in every language other than PHP <http://www.phpsadness.com/sad/30&gt;\. Dropping the parens there is equivalent.

(That said, if I hadn't known that already it wouldn't have been something I could infer from the syntax. I'd have to assume the author knew what they were doing. And I'm the sort who will parenthesize && expressions within || expressions, even though it's not strictly necessary.)

Jordan

···

On Dec 13, 2015, at 8:11, Jakob Egger via swift-evolution <swift-evolution@swift.org> wrote:

But there is one good side to this proposal: it nests more naturally than the ternary operator:
"if cond then expr1 else if cond2 then expr2 else expr3"
vs.
"cond ? expr1 : (cond2 ? expr2 : expr3)

Would the cases need to be comma separated? Would a new line make more sense instead?

Currently this is possible:

enum Col { case Red, Green, Blue }

let c = Col.Blue

let x: Int = {
  switch c {
  case .Red: return 1
  case .Green: return 2
  case .Blue: return 3
  }
}()

It works, but there are several things I don’t like:
- the switch statement must be wrapped in a closure which is invoked at the end.
- the type of ‘x’ needs to be given
- each case requires a return statement

Here’s a proposal for a switch expression:

let y = switch c then {
  .Red: 1
  .Green: 2
  .Blue: 3
}

I think the braces are probably needed in the switch expression, also the ‘then’ keyword’ does look a bit peculiar. Any other ideas on how to support both switch statements and expressions?

Al

···

On 12 Dec 2015, at 14:48, Paul Ossenbruggen <possen@gmail.com> wrote:

Dropping “case” might be interesting, since it becomes a little redundant in the “switch” situation, this is one advantage of having a new keyword, but not sure this reads as well:

let v = switch val then .Red: 1, .Green: 2, .Blue: 3

It is definitely nice in it’s compactness which is a big plus.

Another possibility, because “switch" does not need to resolve the syntactic ambiguity, but then we lose the “then” always meaning an expression consistency.

let v = switch val case .Red: 1, case .Green: 2, case .Blue: 3

this might be better for switch because we don’t need to mix “then” with “switch” which historically has not been done. Question is, is it better to go with “then” as expression consistency or with slightly more compact and following the conventions out there. Personally, I am not bothered by using “then” with “switch”

Thanks everyone for the feedback! I will look at it in detail and address or incorporate what makes sense for the proposed approach.

Using fully-fledged if/switch-statements as expressions is another proposal and discussion (which already exists).

can you point me to this?

···

On Dec 13, 2015, at 7:09 AM, Marc Knaup via swift-evolution <swift-evolution@swift.org> wrote:

Using fully-fledged if/switch-statements as expressions is another proposal and discussion (which already exists).

The replacement of the ternary operator should be just syntactic sugar for the other proposal to have a shorter version of "let x = if a {} else {}".

Regarding the "then" keyword:
What about "do"?

let x = if a do b else c

Yes, it reads a bit weird, but as if & switch statements are moving towards being expressions already then "do" blocks will likely too.

So the above example would just be another shortcut for

let x = if a { do { b } } else { c }

On Sun, Dec 13, 2015 at 3:56 PM, Taras Zakharko via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
Hi Paul,

what bothers me in your proposal is that you seem to allow only simple expressions. But it is often the case that one needs to have multiple statements to set up the value. For example:

  let data = if connection.valid
    connection.cached_data
  else {
    // generate the data again
}

I have been thinking a bit about how to implement this in connection with the idea of code blocks as closures proposal I have posted earlier (https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20151207/002056.html\). Switch is a bit more complicated, but I think that the existing if statement can be easily turned into expression:

   func if_<T>(condition: Bool, then_: (()->T)?, else_: (()->T)?) -> T? {
    var result: T?
    
    if condition {
        result = then_?()
    } else {
        result = else_?()
    }
    
    return result
}

the compiler would then translate all if statements into

   if_(condition, then_: then block, else_: else block)

if the else block is not present, it will be set to nil. In that case the if expression also evaluates to nil. Now, if the if is used as a statement, the above transformation is sufficient and the return value will be optimised away by the compiler. If the expression form is used (i.e. there is an assignment operation), the compiler will forcefully unwrap the result:

let x = if_(condition, then_: then block, else_: else block)!

This way, if else block is absent, the program will crash. A bit of tweaking will also generate a useful error message. I am also sure that it is possible to generate a warning (or even an error) at the compile time without too much effort.

I think the nice thing about this proposal is that it uses already existing mechanisms in the language and only requires some minimal transformations by the compiler.

The switch expression can be approached in a similar way, but would require more compiler magic.

Best,

Taras

On 13 Dec 2015, at 06:54, Paul Ossenbruggen via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and switch expressions based upon the discussions we had here. I have tried to keep the scope of the changes as small as possible, only added one keyword and kept things as similar to the existing language constructs as possible. If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

On Dec 12, 2015, at 3:51 PM, Paul Ossenbruggen <possen@gmail.com <mailto:possen@gmail.com>> wrote:

Implied in using the “then", if…then…else would aways require “else" when using “then” similar to how “guard" requires “else”. This will help to make the difference between statements and expressions clear.

let x = If cond then X else Y

is the full form, where “else" can not be omitted.

On Dec 12, 2015, at 12:59 PM, Paul Ossenbruggen <possen@gmail.com <mailto:possen@gmail.com>> wrote:

On Dec 12, 2015, at 12:37 PM, Andrey Tarantsov via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

1. I would really hate to explain to someone when if needs a then and when it doesn't. That's the sort of inconsistency that shouldn't be added lightly.

agreed definitely want to be careful with that. I think with braces meaning statements that differentiation can be made clear. I would certainly start with statements when describing, just as you usually don’t talk about the ternary operator until later.

3. If we can somehow solve all of this, I think I'll be +1 for replacing (A ? B : C) with some sort of (if A then B else C).

Yes that would be great.

4. Generally, I wonder how hard would it be for all statements to be usable as expressions? Why didn't Swift go that way from the start?

The biggest problem statement is you don’t need to exhaustively specify every outcome:

if cond {
  print(“hello”)
}

whereas in an expression you have to specify what happens in the else.

let say = if cond then “hello” else “goodbye"

unless you go seriously off the deep end:

let say = if cond then “hello”

“say" then becomes an optional, *shudder*

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

I'm not quite sure how I feel about this specific proposal yet but in general I do want to see conditional expressions and removal of the ternary operator.

I would like to see "else if" included in whatever we adopt as the final solution. Is there a reason this is omitted from this proposal? I apologize if that was discussed in the thread. I haven't followed every post.

Good, point I am thinking that it should behave pretty much as ternary operators but this has not come up in this thread so I will explore it a bit.

if x then if y then “A” else “B" else if y then “C” else “D”

which could be optionally surrounded with parens to help with readability, essentially as you would with ternary operators.

if x then (if y then “A” else “B”) else (if y then “C” else “D”)

···

On Dec 13, 2015, at 5:45 AM, Matthew Johnson <matthew@anandabits.com> wrote:

Sent from my iPad

On Dec 12, 2015, at 11:54 PM, Paul Ossenbruggen via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and switch expressions based upon the discussions we had here. I have tried to keep the scope of the changes as small as possible, only added one keyword and kept things as similar to the existing language constructs as possible. If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

On Dec 12, 2015, at 3:51 PM, Paul Ossenbruggen <possen@gmail.com <mailto:possen@gmail.com>> wrote:

Implied in using the “then", if…then…else would aways require “else" when using “then” similar to how “guard" requires “else”. This will help to make the difference between statements and expressions clear.

let x = If cond then X else Y

is the full form, where “else" can not be omitted.

On Dec 12, 2015, at 12:59 PM, Paul Ossenbruggen <possen@gmail.com <mailto:possen@gmail.com>> wrote:

On Dec 12, 2015, at 12:37 PM, Andrey Tarantsov via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

1. I would really hate to explain to someone when if needs a then and when it doesn't. That's the sort of inconsistency that shouldn't be added lightly.

agreed definitely want to be careful with that. I think with braces meaning statements that differentiation can be made clear. I would certainly start with statements when describing, just as you usually don’t talk about the ternary operator until later.

3. If we can somehow solve all of this, I think I'll be +1 for replacing (A ? B : C) with some sort of (if A then B else C).

Yes that would be great.

4. Generally, I wonder how hard would it be for all statements to be usable as expressions? Why didn't Swift go that way from the start?

The biggest problem statement is you don’t need to exhaustively specify every outcome:

if cond {
  print(“hello”)
}

whereas in an expression you have to specify what happens in the else.

let say = if cond then “hello” else “goodbye"

unless you go seriously off the deep end:

let say = if cond then “hello”

“say" then becomes an optional, *shudder*

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

Using fully-fledged if/switch-statements as expressions is another proposal and discussion (which already exists).

The replacement of the ternary operator should be just syntactic sugar for the other proposal to have a shorter version of "let x = if a {} else {}”.

This is the expression vs statement debate and whether they can be made the same. I don’t think they can easily see my response to Taras.

Regarding the "then" keyword:
What about "do"?

let x = if a do b else c

Yes, it reads a bit weird, but as if & switch statements are moving towards being expressions already then "do" blocks will likely too.

So the above example would just be another shortcut for

let x = if a { do { b } } else { c }

This is a possibility if “then” is deemed to useful in other contexts and the feedback is that we don’t want another keyword. I like the readability of “then"

···

On Dec 13, 2015, at 7:09 AM, Marc Knaup via swift-evolution <swift-evolution@swift.org> wrote:

On Sun, Dec 13, 2015 at 3:56 PM, Taras Zakharko via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:
Hi Paul,

what bothers me in your proposal is that you seem to allow only simple expressions. But it is often the case that one needs to have multiple statements to set up the value. For example:

  let data = if connection.valid
    connection.cached_data
  else {
    // generate the data again
}

I have been thinking a bit about how to implement this in connection with the idea of code blocks as closures proposal I have posted earlier (https://lists.swift.org/pipermail/swift-evolution/Week-of-Mon-20151207/002056.html\). Switch is a bit more complicated, but I think that the existing if statement can be easily turned into expression:

   func if_<T>(condition: Bool, then_: (()->T)?, else_: (()->T)?) -> T? {
    var result: T?
    
    if condition {
        result = then_?()
    } else {
        result = else_?()
    }
    
    return result
}

the compiler would then translate all if statements into

   if_(condition, then_: then block, else_: else block)

if the else block is not present, it will be set to nil. In that case the if expression also evaluates to nil. Now, if the if is used as a statement, the above transformation is sufficient and the return value will be optimised away by the compiler. If the expression form is used (i.e. there is an assignment operation), the compiler will forcefully unwrap the result:

let x = if_(condition, then_: then block, else_: else block)!

This way, if else block is absent, the program will crash. A bit of tweaking will also generate a useful error message. I am also sure that it is possible to generate a warning (or even an error) at the compile time without too much effort.

I think the nice thing about this proposal is that it uses already existing mechanisms in the language and only requires some minimal transformations by the compiler.

The switch expression can be approached in a similar way, but would require more compiler magic.

Best,

Taras

On 13 Dec 2015, at 06:54, Paul Ossenbruggen via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and switch expressions based upon the discussions we had here. I have tried to keep the scope of the changes as small as possible, only added one keyword and kept things as similar to the existing language constructs as possible. If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

On Dec 12, 2015, at 3:51 PM, Paul Ossenbruggen <possen@gmail.com <mailto:possen@gmail.com>> wrote:

Implied in using the “then", if…then…else would aways require “else" when using “then” similar to how “guard" requires “else”. This will help to make the difference between statements and expressions clear.

let x = If cond then X else Y

is the full form, where “else" can not be omitted.

On Dec 12, 2015, at 12:59 PM, Paul Ossenbruggen <possen@gmail.com <mailto:possen@gmail.com>> wrote:

On Dec 12, 2015, at 12:37 PM, Andrey Tarantsov via swift-evolution <swift-evolution@swift.org <mailto:swift-evolution@swift.org>> wrote:

1. I would really hate to explain to someone when if needs a then and when it doesn't. That's the sort of inconsistency that shouldn't be added lightly.

agreed definitely want to be careful with that. I think with braces meaning statements that differentiation can be made clear. I would certainly start with statements when describing, just as you usually don’t talk about the ternary operator until later.

3. If we can somehow solve all of this, I think I'll be +1 for replacing (A ? B : C) with some sort of (if A then B else C).

Yes that would be great.

4. Generally, I wonder how hard would it be for all statements to be usable as expressions? Why didn't Swift go that way from the start?

The biggest problem statement is you don’t need to exhaustively specify every outcome:

if cond {
  print(“hello”)
}

whereas in an expression you have to specify what happens in the else.

let say = if cond then “hello” else “goodbye"

unless you go seriously off the deep end:

let say = if cond then “hello”

“say" then becomes an optional, *shudder*

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org <mailto:swift-evolution@swift.org>
https://lists.swift.org/mailman/listinfo/swift-evolution

"or we could go with an optional “then” for statements as was suggested by
Thorsten. "

I don't think this should go in the proposal. An else is alway required in
a guard statement, an expression should not return an optional imho.

···

On Sunday, December 13, 2015, Paul Ossenbruggen via swift-evolution < swift-evolution@swift.org> wrote:

On Dec 13, 2015, at 8:11 AM, Jakob Egger <jakob@eggerapps.at > <javascript:_e(%7B%7D,'cvml','jakob@eggerapps.at');>> wrote:

I really don't like the "if cond then expr1 else expr2".

1) First of all, it's extremely verbose. It's almost as bad as the SQL
construct "case when cond then expr1 else expr2 end”.

Yeah it adds a few characters overall. What used to be 2 chars now takes
10. Clarity is preferred though by many. I head frequently people telling
users to never use ternary operators because they are confusing to read.

2) It makes Swift harder to learn. Newcomers will be confused why you
sometimes need to use curly braces and why at other times you need to use
the "then" keyword.

I did mention this in Alternatives Considered section. By making the else
part required, this emphasizes that it is different or we could go with an
optional “then” for statements as was suggested by Thorsten.

3) It doesn't help when you want to do multi-line calculations

This is the case with the ternary as well, I think it is better to keep it
simple.

But there is one good side to this proposal: it nests more naturally than
the ternary operator:
"if cond then expr1 else if cond2 then expr2 else expr3"
vs.
"cond ? expr1 : (cond2 ? expr2 : expr3)

The proposed syntax for the switch statement is so confusing that I really
don't think it is a good idea.

Not sure why that is, it is essentially the same as the existing switch
statement except everything is an expression instead of statements. Is
there anything I can do in the examples or documentation to make things
clearer?

Why not just allow normal if statements to return values?
I don't see what's so bad about the following:
"let value = if cond {expr1} else {expr2}"

This would also extend to multiple lines:
let value = if cond {
  expr1
} else {
  let something = Object()
  something.doStuff()
  something
}

I answered this with others, also notice how there are braces everywhere?
does that really work when you just want to put something on one line. What
happens when one of your branches returns void? Expressions are guaranteed
to have a result, statements don’t make such a guarantee.

Jakob

On 13 Dec 2015, at 06:54, Paul Ossenbruggen via swift-evolution < > swift-evolution@swift.org > <javascript:_e(%7B%7D,'cvml','swift-evolution@swift.org');>> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and
switch expressions based upon the discussions we had here. I have tried to
keep the scope of the changes as small as possible, only added one keyword
and kept things as similar to the existing language constructs as possible.
If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

I also have no preference yet so I'll just throw in some thoughts.

** Existing Code **
The removal of the ternary operator would likely affect a lot of existing
code.
A quick search for " ? " (with spaces) over a large app of our team yields
304 results.

Two simpler examples:

[
  "With Conditions": hasReport ? "yes" : "no",
  "With Image": hasImage ? "yes" : "no",
  "With Message": hasMessage ? "yes" : "no",
  "Shared on Facebook Profile": sharedOnFacebookProfile ? "yes" : "no",
  "Shared in Facebook Group": sharedOnFacebookGroup ? "yes" : "no",
  "Shared on Facebook Page": sharedOnFacebookPage ? "yes" : "no"
]

view1.alpha = editing ? 1 : 0
view2.alpha = editing ? 1 : 0
view3.alpha = editing ? 0 : 1
view4.alpha = editing ? 1 : 0

I am not sure using if…then…else would make this better to read &
understand or worse.

** Keyword then **
Making then a keyword would also cost us another word so that change needs
to be carefully considered.
In our large app I found just a single instance where then was used for a
variable's name:

func reloadConfigurationAndThen(then: () -> Void) { … }

Promises use the word then rather extensively: https://promisesaplus.com

···

On Sun, Dec 13, 2015 at 2:45 PM, Matthew Johnson via swift-evolution < swift-evolution@swift.org> wrote:

I'm not quite sure how I feel about this specific proposal yet but in
general I do want to see conditional expressions and removal of the ternary
operator.

I would like to see "else if" included in whatever we adopt as the final
solution. Is there a reason this is omitted from this proposal? I
apologize if that was discussed in the thread. I haven't followed every
post.

Sent from my iPad

On Dec 12, 2015, at 11:54 PM, Paul Ossenbruggen via swift-evolution < > swift-evolution@swift.org> wrote:

Hello All,

Been sick in bed all day, but decided to try to be productive…

I did a rough draft of a proposal for implementing if expressions and
switch expressions based upon the discussions we had here. I have tried to
keep the scope of the changes as small as possible, only added one keyword
and kept things as similar to the existing language constructs as possible.
If anyone wants to help me with this, or has feedback, please let me know,

https://github.com/possen/swift-evolution/blob/master/0020.md

Thanks,
- Paul

On Dec 12, 2015, at 3:51 PM, Paul Ossenbruggen <possen@gmail.com> wrote:

Implied in using the “then", if…then…else would aways require “else" when
using “then” similar to how “guard" requires “else”. This will help to
make the difference between statements and expressions clear.

let x = If cond then X else Y

is the full form, where “else" can not be omitted.

On Dec 12, 2015, at 12:59 PM, Paul Ossenbruggen <possen@gmail.com> wrote:

On Dec 12, 2015, at 12:37 PM, Andrey Tarantsov via swift-evolution < > swift-evolution@swift.org> wrote:

1. I would really hate to explain to someone when *if* needs a *then* and
when it doesn't. That's the sort of inconsistency that shouldn't be added
lightly.

agreed definitely want to be careful with that. I think with braces
meaning statements that differentiation can be made clear. I would
certainly start with statements when describing, just as you usually don’t
talk about the ternary operator until later.

3. If we can somehow solve all of this, I think I'll be +1 for replacing
(A ? B : C) with some sort of (*if* A *then* B *else* C).

Yes that would be great.

4. Generally, I wonder how hard would it be for all statements to be
usable as expressions? Why didn't Swift go that way from the start?

The biggest problem statement is you don’t need to exhaustively specify
every outcome:

if cond {
print(“hello”)
}

whereas in an expression you have to specify what happens in the else.

let say = if cond then “hello” else “goodbye"

unless you go seriously off the deep end:

let say = if cond then “hello”

“say" then becomes an optional, *shudder*

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

Good point Jordan. I think what Jakob was trying to say is that 'else if'
is already a language construct, and thus it might be easier on the eye to
see 'if cond then expr1 else if cond2 then expr2 ...', than to see 'cond1 ?
expr1 : cond2 ? expr2 : ...'

···

On Mon, Dec 14, 2015 at 6:38 PM Jordan Rose via swift-evolution < swift-evolution@swift.org> wrote:

On Dec 13, 2015, at 8:11, Jakob Egger via swift-evolution < > swift-evolution@swift.org> wrote:

But there is one good side to this proposal: it nests more naturally than
the ternary operator:
"if cond then expr1 else if cond2 then expr2 else expr3"
vs.
"cond ? expr1 : (cond2 ? expr2 : expr3)

Without commenting on anything else in this thread, ?: nests properly
(right-associative-ly) in every language other than PHP
<http://www.phpsadness.com/sad/30&gt;\. Dropping the parens there is
equivalent.

(That said, if I hadn't known that already it wouldn't have been something
I could infer from the syntax. I'd have to assume the author knew what they
were doing. And I'm the sort who will parenthesize && expressions within ||
expressions, even though it's not strictly necessary.)

Jordan
_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution