Functions 2
How to provide default values for parameters
Say we want to provide a default value for a parameter. Ex:
func printTimesTables(for number: Int, end: Int) { for i in 1...end { print("\(i) x \(number) is \(i * number)") } } printTimesTables(for: 5, end: 20)
We can do:
func printTimesTables(for number: Int, end: Int = 12) { for i in 1...end { print("\(i) x \(number) is \(i * number)") } } printTimesTables(for: 5, end: 20) printTimesTables(for: 8)
Or:
func findDirections(from: String, to: String, route: String = "fastest", avoidHighways: Bool = false) { // code here }
Now these are legal:
findDirections(from: "London", to: "Glasgow") findDirections(from: "London", to: "Glasgow", route: "scenic") findDirections(from: "London", to: "Glasgow", route: "scenic", avoidHighways: true)
Scored 9/12 on default parameters
How to handle errors in functions
studysubject
We need to handle errors gracefully or our code will crash.
Error handling in Swift looks like this:
- Telling swift about the possible errors that can happen.
- Write a function that can flag up errors if they heppen.
- Calling the function and handling the error.
Defining possible errors
enum PasswordError: Error { case short, obvious }
Write a function that triggers the errors
func checkPassword(_ password: String) throws -> String { if password.count < 5 { throw PasswordError.short } if password == "12345" { throw PasswordError.obvious } if password.count < 8 { return "OK" } else if password.count < 10 { return "Good" } else { return "Excellent" } }
Note: Being marked with
throws
doesn’t mean the function will throw, only that it can throw.
Handling errors look like this
let string = "12345" do { let result = try checkPassword(string) print("Password rating: \(result)") } catch { print("There was an error.") }
The try
keyword needs to be inside a do...catch
block. You can also use !try
which can work without the do...catch
however the code will crash if an error is thrown.
You must have a default catch for every kind of error. You can also have specific catches for specific errors as well:
let string = "12345" do { let result = try checkPassword(string) print("Password rating: \(result)") } catch PasswordError.short { print("Please use a longer password.") } catch PasswordError.obvious { print("I have the same combination on my luggage!") } catch { print("There was an error.") }
Note:
try
is used before functions that can throw.
do { try throwingFunction1() nonThrowingFunction1() try throwingFunction2() nonThrowingFunction2() try throwingFunction3() } catch { // handle errors }
Scored 7/12 on writing throwing functions. I could use a re-read of this subject. Though I will say out the first 6 questions, I only got 1 right. It also was 4AM. Stopped immediately. Woke up and finished questions 7-12 and got each of those correct.
Scored 6/6 on running throwing functions.
Summary: Functions
- Functions allow for code reuse
- Functions start with the word
func
followed by the name of the function, then curly braces. - Adding parameters make the functions more flexible
- Parameter names can be controlled externally with the
_
. The parameter name is followed by the type ex:parameterName: type
- Provide a default for parameters you use repeatedly, this improves the conciseness of the function
- Use a tuple to return multiple pieces of data from a function
- If your function throws errors, define an enum with the error cases and throw within your functions as necessary. Use
do, try... catch
to handle them at the call site