Anyways, you're entirely free to use a named return value in the second (or later) part of a multi valued := statement. An example is noted below, the clunky and obvious branches are there, but the intent and flow is obvious at a glance.
Anyways, you're entirely free to use a named return value in the second (or later) part of a multi valued := statement. An example is noted below, the clunky and obvious branches are there, but the intent and flow is obvious at a glance.
[1] https://go.googlesource.com/proposal/+/master/design/go2draf... [2] https://github.com/golang/go/issues/32437#issuecomment-51203...
Effective Go, on if: https://golang.org/doc/effective_go#if
It only promotes the concept that of using guard-clause style ifs that return an error and have no else clause, gradually eliminating each possible error condition. This style of programming was later termed in the Go community "Aligning the happy path to the left"[1][2]
[1] https://medium.com/@matryer/line-of-sight-in-code-186dd7cdea... [2] https://maelvls.dev/go-happy-line-of-sight/
I wholeheartedly agree that this style makes code more readable and I have adopted it - and encouraged others to adopt it - in other languages besides Go. This style would stil be followed with the try or check/handle proposals. For instance, let's take the example:
f, err := os.Open(name)
if err != nil {
return err
}
d, err := f.Stat()
if err != nil {
f.Close()
return err
}
codeUsing(f, d)
f.Close()
return nil
With the simple try proposal that would be: f := try(os.Open(name))
defer f.Close()
d := try(f.Stat())
codeUsing(f, d)
With OP's variant of the try proposal, using a question mark this is arguably even more readable (less noisy): f := os.Open(name)?
defer f.Close()
d := f.Stat()?
codeUsing(f, d)
As you can see, these proposal reduce - not increase - nesting, so they are completely in line with what Effective Go is saying.