[swift-evolution] Idea: Extend "guard" to try-statements, with a catch block

Jacob Bandes-Storch jtbandes at gmail.com
Mon Feb 29 15:30:11 CST 2016


Thanks for the feedback, Stephen.

On Mon, Feb 29, 2016 at 1:03 PM, Stephen Celis <stephen.celis at gmail.com>
wrote:

> > On Feb 29, 2016, at 3:09 PM, Jacob Bandes-Storch via swift-evolution <
> swift-evolution at swift.org> wrote:
> >
> > - If Swift's error-handling mechanisms evolved into a first-class Result
> type, would this proposal be moot?
>
> Could you clarify what you mean by this?
>

I didn't think through it very far, which is why I put it under "discussion
topics" rather than fleshing it out :-)

I guess I'm just wondering whether the syntax for optionals/errors might
change significantly enough with the introduction of Result that it
wouldn't make sense to introduce this feature now.

Suppose we had "enum Result<T> { case Some(T), Error(ErrorType) }". Then
"throws" might be syntactic sugar: "foo() throws -> T" would be the same as
"foo() -> Result<T>". Using today's syntax, you could handle Results using
switch:

    switch foo() {
    case .Some(let x):
        // use x
    case .Error(let error):
        // use error
    }

But conceivably the Result would be treated with more first-class syntax:

    if let x = try foo() {
        // handle .Some
    } catch {
        // handle .Error
    }

The more I think about this, it doesn't seem too different from what I
proposed, so I guess it's not worth worrying about conflicts.


>
> > - Would this make sense as a feature of pattern-matching, rather than
> just "guard", so you could also do "if case let x = try foo() { ... } catch
> { ... }" ?
>
> This makes sense to me at first glance, though it makes things rather
> complicated.
>
>   - Can `catch` blocks appear before `else [if]` blocks? E.g.,
>
>         if try test() != nil {
>             ...
>         } catch {
>             ...
>         } else if try test2() != nil {
>             ...
>         } else {
>             ...
>         } catch {
>             ...
>         }
>

That's an interesting point. I can't see why this shouldn't be allowed.
Would you be able to handle all errors at the end?

    e.g.: if case let x = try foo() { ... } else if case let y = try bar()
{ ... } catch { /*handle errors from both expressions*/ }



>
>   - Are `if`/`else` blocks generally promoted to `do`-like state when
> `catch` blocks exist?
>
>         if something() {
>             try failable()
>         } catch {
>             ...
>         }
>

Hmm. I think I would like this, but there may have been reasons for not
allowing this sort of thing. I can't recall if it's been discussed before.
What do others think?


>
>   - Does this extend to `switch` and how?
>

Maybe just the same thing: "switch try foo() { ... } catch { ... }" ?
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://lists.swift.org/pipermail/swift-evolution/attachments/20160229/aa310581/attachment.html>


More information about the swift-evolution mailing list