Countless times I have to write try statements and most circumstances require me have a guard statement in place so I dont have a optional object. is there a way we can add catch blocks in guard statements to do better handling. I say this because I h8 "do-catch" blocks . Something like below is what I am thinking. Instead of "guard-else", you can add "guard-catch". The example below shows a readDisk func that has "throws" and returns an optional.
// func readDisk() throws -> DiskObject?
guard let response = try? readDisk(from: "someDirectory") catch {
let _ = ShowAlert()
return
}
jrose
(Jordan Rose)
August 10, 2018, 4:14pm
2
This has come up many times before. It would probably be better to pick up one of those threads instead of making a new one.
I’d like to propose a guard/catch construct to the language. It would allow code to use throwing functions and handle errors fully, without straying from a happy path. do/catch can be a bit heavy-handed sometimes, and it would be nice to be able to handle throwing functions without committing to all the nesting and ceremony of do/catch.
Full proposal, which discusses all the corner cases and alternatives:
Looking forward to feedback!
Soroush
This messages was modified from the original accidentally sent out privately, earlier.
FYI this works today in Xcode 9.0 beta 2 playgrounds:
class X {
init() throws {}
func foo() {
print( "Things succeeded" )
}
}
func bar() throws -> X { return try X() }
func f()
{
guard let x1:X = try? X(), let x2:X = try? bar() else {
print( "Things failed ")
return
}
x1.foo()
x2.foo()
}
f() // works
Most of the examples of this proposed featu…
Hello dear Swift community,
this proposal might seem like some new syntax sugar, but it also aims to escape the 'do { }' scope from the 'do try catch‘ mechanism while making the existing error handling more powerful.
Lets assume we have some sort of network type, which can throw a ton of different errors:
struct TCPListener {
init(address: String) throws { /* implement */ }
func accept() throws -> TCPConn { /* implement */ }
/* ... */
}
A way of implimentation might look like…
Guard statements interact with pattern-matching to ensure that control flow
cannot continue unless a pattern is matched. This is a very convenient way
to introduce non-optional variables from optional-valued expressions:
// func foo() -> T? ...
guard let x = foo() *else* {
// the compiler does not allow control flow to escape this block
}
// control flow cannot reach here if foo() returned nil
Guard statements can be used with the optional form "*try?*" to provide…
3 Likes
Understood. Thanks for the Swift reply
2 Likes