When coding with conditionals, the left-hand margin of the code should be the "golden" or "happy" path. That is, don't nest if
statements. Multiple return statements are OK. The guard
statement is built for this.
Preferred:
func computeFFT(context: Context?, inputData: InputData?) throws -> Frequencies {
guard let context = context else {
throw FFTError.noContext
}
guard let inputData = inputData else {
throw FFTError.noInputData
}
// use context and input to compute the frequencies
return frequencies
}
Not Preferred:
func computeFFT(context: Context?, inputData: InputData?) throws -> Frequencies {
if let context = context {
if let inputData = inputData {
// use context and input to compute the frequencies
return frequencies
} else {
throw FFTError.noInputData
}
} else {
throw FFTError.noContext
}
}
When multiple optionals are unwrapped either with guard
or if let
, minimize nesting by using the compound version when possible. In the compound version, place the guard
on its own line, then ident each condition on its own line. The else
clause is indented to match the conditions and the code is indented one additional level, as shown below. Example:
Preferred:
guard
let number1 = number1,
let number2 = number2,
let number3 = number3
else {
fatalError("impossible")
}
// do something with numbers
Not Preferred:
if let number1 = number1 {
if let number2 = number2 {
if let number3 = number3 {
// do something with numbers
} else {
fatalError("impossible")
}
} else {
fatalError("impossible")
}
} else {
fatalError("impossible")
}