This is my research notebook. I'm an OSX / iOS indie developer. After 8 years of Objective-C I really enjoy Swift nowadays. Trying to publish all my research on Development, Swift & other technologies here.
Among the new features that Swift offers to Objective-C programmers is one that disguises itself like a boring old man while it offers huge potential for forming elegant solutions to otherwise unwieldy sets of nested branches. I'm, of course talking about the switch statement that many Objective-C programmers probably consider as a clunky syntax device which is most entertaining when used as Duff's Device, yet usually offers little to no advantages over multiple if statements.
The Switch statement in Swift can do much more though. In the following tutorial, I will try to explain the various usages for these new features in more detail. I'll mostly ignore those solutions where there's no benefit over how switch works in Objective-C or C. The basics of this post were actually written in July 2014, but so many of my patterns crashed the compiler back then that I postponed writing it until there's better support.
This Blog Post is also available in the following languages:
1 Diving In
The main feature of switch is of course pattern matching, the ability to destructure values and match different switch cases based on correct match of the values to the cases.
// Example of the worst binary -> decimal converter in history
let bool1 = 1
let bool2 = 0
switch (bool1, bool2) {
case (0, 0): print("0")
case (0, 1): print("1")
case (1, 0): print("2")
case (1, 1): print("3")
}
Pattern matching has long existed in other languages like Haskell, Erlang, Scala, or Prolog. This is a boon, because it allows us to have a look at how those languages utilize pattern matching in order to solve their problems. We can even have a look at their examples to find the most practical ones that offer real world adaptability.
2 A Trading Engine
So Wall Street contacted you, they need a new trading platform running on iOS devices. As it is a trading platform, you define an enum for trades.
2.1 First Draft
enum Trades {
case Buy(stock: String, amount: Int, stockPrice: Float)
case Sell(stock: String, amount: Int, stockPrice: Float)
}
You were also handed the following API to handle trades. Notice how sell orders are just negative amounts. And you're told the stock price is not important, their engine will take an internal one anyway.
/**
- parameter stock: The stock name
- parameter amount: The amount, negative number = sell, positive = buy
*/
func process(stock: String, _ amount: Int) {
print ("\(amount) of \(stock)")
}
The next step is to process those trades. You see the potential for using pattern matching and write this:
let aTrade = Trades.Buy(stock: "APPL", amount: 200, stockPrice: 115.5)
switch aTrade {
case .Buy(let stock, let amount, _):
process(stock, amount)
case .Sell(let stock, let amount, _):
process(stock, amount * -1)
}
// Prints "buy 200 of APPL"
Swift lets us conveniently only destructure / extract the information from the enum that we really want. In this case only the stock and the amount.
Awesome, you visit Wall Street to show of your fantastic trading platform. However, as always, the reality is much more cumbersome than the beautiful theory. Trades aren't trades you learn.
You have to calculate in a fee which is different based on the trader type.
The smaller the institution the higher the fee.
Also, bigger institutions get a higher priority.
They also realized that you'll need a new API for this, so you were handed this:
So you go back to the drawing board and add another enum. The trader type is part of every trade, too.
enum TraderType {
case SingleGuy
case Company
}
enum Trades {
case Buy(stock: String, amount: Int, stockPrice: Float, type: TraderType)
case Sell(stock: String, amount: Int, stockPrice: Float, type: TraderType)
}
So, how do you best implement this new restriction? You could just have an if / else switch for buy and for sell, but that would lead to nested code which quickly lacks clarity - and who knows maybe these Wall Street guys come up with further complications. So you define it instead as additional requirements on the pattern matches:
let aTrade = Trades.Sell(stock: "GOOG", amount: 100, stockPrice: 666.0, type: TraderType.Company)
switch aTrade {
case let .Buy(stock, amount, _, TraderType.SingleGuy):
processSlow(stock, amount, 5.0)
case let .Sell(stock, amount, _, TraderType.SingleGuy):
processSlow(stock, -1 * amount, 5.0)
case let .Buy(stock, amount, _, TraderType.Company):
processFast(stock, amount, 2.0)
case let .Sell(stock, amount, _, TraderType.Company):
processFast(stock, -1 * amount, 2.0)
}
The beauty of this is that there's a very succinct flow describing the different possible combinations.
Also, note how we changed .Buy(let stock, let amount) into let .Buy(stock, amount) in order to keep things simpler. This will destructure the enum just as before, only with less syntax.
2.3 Guards! Guards!
Once again you present your development to your Wall Street customer, and once again a new issue pops up (you really should have asked for a more detailed project description).
Sell orders exceeding a total value of $1.000.000 do always get fast handling, even if it's just a single guy.
Buy orders under a total value of $1.000 do always get slow handling.
With traditional nested if syntax, this would already become a bit messy. Not so with switch. Swift includes guards for switch cases which allow you to further restrict the possible matching of those cases.
You only need to modify your switch a little bit to accommodate for those new changes
let aTrade = Trades.Buy(stock: "GOOG", amount: 1000, stockPrice: 666.0, type: TraderType.SingleGuy)
switch aTrade {
case let .Buy(stock, amount, _, TraderType.SingleGuy):
processSlow(stock, amount, 5.0)
case let .Sell(stock, amount, price, TraderType.SingleGuy)
where price*Float(amount) > 1000000:
processFast(stock, -1 * amount, 5.0)
case let .Sell(stock, amount, _, TraderType.SingleGuy):
processSlow(stock, -1 * amount, 5.0)
case let .Buy(stock, amount, price, TraderType.Company)
where price*Float(amount) < 1000:
processSlow(stock, amount, 2.0)
case let .Buy(stock, amount, _, TraderType.Company):
processFast(stock, amount, 2.0)
case let .Sell(stock, amount, _, TraderType.Company):
processFast(stock, -1 * amount, 2.0)
}
This code is quite structured, still rather easy to read, and wraps up the complex cases quite well.
That's it, we've successfully implemented our trading engine. However, this solution still has a bit of repetition; we wonder if there're pattern matching ways to improve upon that. So, let's look into pattern matching a bit more.
3 Advanced Pattern Matching
So now we've seen several patterns in action. But what's the syntax here? Which other things can we match for? Swift distinguishes 7 different patterns. We're going to have a quick look at each of them.
All of those patterns can not only be used with the switch keyword, but also with the if, guard, and for keywords. For details on this, see below.
3.1 1. Wildcard Pattern
The wildcard pattern ignores the value to be matched against. In this case any value is possible. This is the same pattern as let _ = fn() where the _ indicates that you don't wish to further use this value. The interesting part is that this matches all values including nil1. You can even match optionals by appending a ?:
let p: String? = nil
switch p {
case _?: print ("Has String")
case nil: print ("No String")
}
As you've seen in the trading example, it also allows you to omit the data you don't need from matching enums or tuples:
switch (15, "example", 3.14) {
case (_, _, let pi): print ("pi: \(pi)")
}
3.2 2. Identifier Pattern
Matches a concrete value. This is how things work in Objective-C's switch implementation:
switch 5 {
case 5: print("5")
}
3.3 3. Value-Binding Pattern
This is the very same as binding values to variables via let or var. Only in a switch statement. You've already seen this before, so I'll provide a very short example:
switch (4, 5) {
case let (x, y): print("\(x) \(y)")
}
let age = 23
let job: String? = "Operator"
let payload: AnyObject = NSDictionary()
switch (age, job, payload) {
case (let age, _?, _ as NSDictionary):
print(age)
default: ()
}
Here, we're combining three values into a tuple (imagine they're coming from different API calls) and matching them in one go. Note that the pattern achieves three things:
It extracts the age
It makes sure there is a job, even though we don't need it
It makes sure that the payload is of kind NSDictionary even though we don't need the actual value either.
3.5 5. Enumeration Case Pattern
As you saw in our trading example, pattern matching works really great with Swift's enums. That's because enum cases are like sealed, immutable, destructable structs. Much like with tuples, you can unwrap the contents of an individual case right in the match and only extract the information you need 2.
Imagine you're writing a game in a functional style and you have a couple of entities that you need to define. You could use structs but as your entities will have very little state, you feel that that's a bit of an overkill.
enum Entities {
case Soldier(x: Int, y: Int)
case Tank(x: Int, y: Int)
case Player(x: Int, y: Int)
}
Now you need to implement the drawing loop. Here, we only need the X and Y position:
for e in entities() {
switch e {
case let .Soldier(x, y):
drawImage("soldier.png", x, y)
case let .Tank(x, y):
drawImage("tank.png", x, y)
case let .Player(x, y):
drawImage("player.png", x, y)
}
}
3.6 6. Type-Casting Patterns
As the name already implies, this pattern casts or matches types. It has two different keywords:
istype: Matches the runtime type (or a subclass of it) against the right hand side. This performs a type cast but disregards the returned type. So your case block won't know about the matched type.
pattern astype: Performs the same match as the is pattern but for a successful match casts the type into the pattern specified on the left hand side.
Here is an example of the two.
let a: Any = 5
switch a {
// this fails because a is still anyobject
// error: binary operator '+' cannot be applied to operands of type 'Any' and 'Int'
case is Int: print (a + 1)
// This works and returns '6'
case let n as Int: print (n + 1)
default: ()
}
Note that there is no pattern before the is. It matches directly against a.
3.7 7. Expression Pattern
The expression pattern is very powerful. It matches the switch value against an expression implementing the ~= operator. There're default implementations for this operator, for example for ranges, so that you can do:
switch 5 {
case 0..10: print("In range 0-10")
}
However, the much more interesting possibility is overloading the operator yourself in order to add matchability to your custom types. Let's say that you decided to rewrite the soldier game we wrote earlier and you want to use structs after all.
struct Soldier {
let hp: Int
let x: Int
let y: Int
}
Now you'd like to easily match against all entities with a health of 0. We can simply implement the ~= operators as follows.
But this is rather cumbersome and defeats the purpose of a lot of the magic behind pattern matching.
In an earlier version of this post, I wrote that ~= doesn't work with protocols, but I was wrong. I remember that I tried it in a Playground, and it didn't work. However, this example (as kindly provided by latrodectus on reddit) does work fine:
protocol Entity {
var value: Int {get}
}
struct Tank: Entity {
var value: Int
init(_ value: Int) { self.value = value }
}
struct Peasant: Entity {
var value: Int
init(_ value: Int) { self.value = value }
}
func ~=(pattern: Entity, x: Entity) -> Bool {
return pattern.value == x.value
}
switch Tank(42) {
case Peasant(42): print("Matched") // Does match
default: ()
}
This completes list of possible switch patterns. Before we move on, there's one final thing to discuss.
3.8 Fallthrough, Break, and Labels
The following is not directly related to pattern matching but only affects the switch keyword, so I'll keep it brief. By default, and unlike C/C++/Objective-C, switchcases do not fall through into the next case which is why in Swift, you don't need to write break for every case. You can opt into traditional fallthrough behaviour with the fallthrough keyword.
switch 5 {
case 5:
print("Is 5")
fallthrough
default:
print("Is a number")
}
// Will print: "Is 5" "Is a number"
Alternatively, you can use break to break out of a switch statement early. Why would you do that if there's no default fallthrough? For example if you can only realize within the case that a certain requirement is not met and you can't execute the case any further:
let userType = "system"
let userID = 10
switch (userType, userID) {
case ("system", _):
guard let userData = getSystemUser(userID) else { break }
print("user info: \(userData)")
insertIntoRemoteDB(userData)
default: ()
}
... more code that needs to be executed
Here, we don't want to call insertIntoRemoteData when the result from getSystemUser is nil. Of course, you could just use an if let here, but if multiple of those cases come together, you quickly end up with a bunch of horrifyingly ugly nested if lets.
But what if you execute your switch in a while loop and you want to break out of the loop, not the switch? For those cases, Swift allows you to define labels to break or continue to:
gameLoop: while true {
switch state() {
case .Waiting: continue gameLoop
case .Done: calculateNextState()
case .GameOver: break gameLoop
}
}
We've discussed the syntax and implementation details of switch and pattern matching.
Now, let us have a look at some interesting (more or less) real world examples.
4 Real World Examples
4.1 Optionals
There're many ways to unwrap optionals, and pattern matching is one of them. You've probably used that quite frequently by now, nevertheless, here's a short example:
var result: String? = secretMethod()
switch result {
case .None:
println("is nothing")
case let a:
println("\(a) is a value")
}
With Swift 2.0, this becomes even easier:
var result: String? = secretMethod()
switch result {
case nil:
print("is nothing")
case let a?:
print("\(a) is a value")
}
As you can see, result could be a string, but it could also be nil. It's an optional. By switching on result, we can figure out whether it is .None or whether it is an actual value. Even more, if it is a value, we can also bind this value to variable right away. In this case a. What's beautiful here, is the clearly visible distinction between the two states, that the variable result can be in.
4.2 Type Matches
Given Swift's strong type system, there's usually no need for runtime type checks like it more often happens in Objective-C. However, when you interact with legacy Objective-C code (which hasn't been updated to reflect simple generics yet), then you often end up with code that needs to check for types. Imagine getting an array of NSStrings and NSNumbers:
let u = NSArray(array: [NSString(string: "String1"), NSNumber(int: 20), NSNumber(int: 40)])
When you go through this NSArray, you never know what kind of type you get. However, switch statements allow you to easily test for types here:
for x in u {
switch x {
case _ as NSString:
print("string")
case _ as NSNumber:
print("number")
default:
print("Unknown types")
}
}
4.3 Applying ranges for grading
So you're writing the grading iOS app for your local Highschool. The teachers want to enter a number value from 0 to 100 and receive the grade character for it (A - F). Pattern Matching to the rescue:
let aGrade = 84
switch aGrade {
case 90...100: print("A")
case 80...90: print("B")
case 70...80: print("C")
case 60...70: print("D")
case 0...60: print("F")
default:
print("Incorrect Grade")
}
4.4 Word Frequencies
We have a sequence of pairs, each representing a word and its frequency in some text. Our goal is to filter out those pairs whose frequency is below or above a certain threshold, and then only return the remaining words, without their respective frequencies.
Here're our words:
let wordFreqs = [("k", 5), ("a", 7), ("b", 3)]
A simple solution would be to model this with map and filter:
let res = wordFreqs.filter({ (e) -> Bool in
if e.1 > 3 {
return true
} else {
return false
}
}).map { $0.0 }
print(res)
However, with flatmap a map that only returns the non-nil elements, we can improve a lot upon this solution. First and foremost, we can get rid of the e.1 and instead have proper destructuring by utilizing (you guessed it) tuples. And then, we only need one call flatmap instead of filter and then map which adds unnecessary performance overhead.
let res = wordFreqs.flatMap { (e) -> String? in
switch e {
case let (s, t) where t > 3: return s
default: return nil
}
}
print(res)
4.5 Directory Traversion
Imagine you want to traverse a file hierachy and find:
all "psd" files from customer1 and customer2
all "blend" files from customer2
all "jpeg" files from all customers.
guard let enumerator = NSFileManager.defaultManager().enumeratorAtPath("/customers/2014/")
else { return }
for url in enumerator {
switch (url.pathComponents, url.pathExtension) {
// psd files from customer1, customer2
case (let f, "psd")
where f.contains("customer1")
|| f.contains("customer2"): print(url)
// blend files from customer2
case (let f, "blend") where f.contains("customer2"): print(url)
// all jpg files
case (_, "jpg"): print(url)
default: ()
}
}
Note that contains stops at the first match and doesn't traverse the complete path.
Again, pattern matching lead to very succinct and readable code.
4.6 Fibonacci
Also, see how beautiful an implementation of the fibonacci algorithm looks with pattern matching 3
func fibonacci(i: Int) -> Int {
switch(i) {
case let n where n <= 0: return 0
case 0, 1: return 1
case let n: return fibonacci(n - 1) + fibonacci(n - 2)
}
}
print(fibonacci(8))
Of course, this will kill your stack with big numbers.
4.7 Legacy API and Value Extractions
Oftentimes, when you get data from an external source, like a library, or an API, it is not only good practice but usually even required that you check the data for consistency before interpreting it. You need to make sure that all keys exists or that the data is of the correct type, or the arrays have the required length. Not doing so can lead from buggy behaviour (missing key) to crash of the app (indexing non-existent array items). The classic way to do this is by nesting if statements.
Let's imagine an API that returns a user. However, there're two types of users: System users - like the administrator, or the postmaster - and local users - like "John B", "Bill Gates", etc. Due to the way the system was designed and grew, there're a couple of nuisances that API consumers have to deal with:
system and local users come via the same API call.
the department key may not exist, since early versions of the db did not have that field and early employees never had to fill it out.
the name array contains either 4 items (username, middlename, lastname, firstname) or 2 items (full name, username) depending on when the user was created.
the age is an Integer with the age of the user
Our system needs to create user accounts for all system users from this API with only the following information: username, department. We only need users born before 1980. If no department is given, "Corp" is assumed.
Given these constraints, let's develop a pattern match for it:
let item = legacyAPI(4)
switch (item["type"], item["department"], item["age"], item["name"]) {
case let (sys as String, dep as String, age as Int, name as [String]) where
age < 1980 &&
sys == "system":
createSystemUser(name.count == 2 ? name.last! : name.first!, dep: dep ?? "Corp")
default:()
}
// returns ("voldemort", "Dark Arts")
Note that this code makes one dangerous assumption, which is that if the name array does not have 2 items, it must have 4 items. If that case doesn't hold, and we get a zero item name array, this would crash.
Other than that, it is a nice example of how pattern matching even with just one case can help you write cleaner code and simplify value extractions.
Also, see how we're writing let at the beginning right after the case, and don't have to repeat it for each assignment within the case.
5 Patterns with other Keywords
The Swift documentation points out, that not all patterns can be used with the if, for or the guard statement. However, the docs seem to be outdated. All 7 patterns work for all three keywords.
For those interested, I compiled an example Gist that has an example for each pattern for each keyword.
As a shorter example, see the Value Binding, Tuple, and Type Casting pattern used for all three keywords in one example:
// This is just a collection of keywords that compiles. This code makes no sense
func valueTupleType(a: (Int, Any)) -> Bool {
// guard case Example
guard case let (x, _ as String) = a else { return false}
print(x)
// for case example
for case let (a, _ as String) in [a] {
print(a)
}
// if case example
if case let (x, _ as String) = a {
print("if", x)
}
// switch case example
switch a {
case let (a, _ as String):
print(a)
return true
default: return false
}
}
let u: Any = "a"
let b: Any = 5
print(valueTupleType((5, u)))
print(valueTupleType((5, b)))
// 5, 5, "if 5", 5, true, false
With this in mind, we will have a short look at each of those keywords in detail.
6 Using for case
With Swift 2.0, pattern matching has become even more important in the language as the switch capabilities have been extended to other keywords as well. For example, let's write a simple array function which only returns the non-nil elements
func nonnil<T>(array: [T?]) -> [T] {
var result: [T] = []
for case let x? in array {
result.append(x)
}
return result
}
print(nonnil(["a", nil, "b", "c", nil]))
The case keyword can be used in for loops just like in switch cases. Here's another example. Remember the game we talked about earlier? Well, after the first refactoring, our entity system now looks like this:
enum Entity {
enum EntityType {
case Soldier
case Player
}
case Entry(type: EntityType, x: Int, y: Int, hp: Int)
}
Fancy, this allows us to draw all items with even less code:
for case let Entity.Entry(t, x, y, _) in gameEntities()
where x > 0 && y > 0 {
drawEntity(t, x, y)
}
Our one line unwraps all the necessary properties, makes sure we're not drawing beyond 0, and finally calls the render call (drawEntity).
In order to see if the player won the game, we want to know if there is at least one Soldier with health > 0
func gameOver() -> Bool {
for case Entity.Entry(.Soldier, _, _, let hp) in gameEntities()
where hp > 0 {return false}
return true
}
print(gameOver())
What's nice is that the Soldier match is part of the for query. This feels a bit like SQL and less like imperative loop programming. Also, this makes our intent clearer to the compiler, opening up the possibilities for dispatch enhancements down the road. Another nice touch is that we don't have to spell out Entity.EntityType.Soldier. Swift understands our intent even if we only write .Soldier as above.
7 Using guard case
Another keyword which supports patterns is the newly introduced guard keyword. You know how it allows you to bind optionals into the local scope much like if let only without nesting things:
func example(a: String?) {
guard let a = a else { return }
print(a)
}
example("yes")
guard let case allows you to do something similar with the power that pattern matching introduces. Let's have a look at our soldiers again. We want to calculate the required HP until our player has full health again. Soldiers can't regain HP, so we should always return 0 for a soldier entity.
let MAX_HP = 100
func healthHP(entity: Entity) -> Int {
guard case let Entity.Entry(.Player, _, _, hp) = entity
where hp < MAX_HP
else { return 0 }
return MAX_HP - hp
}
print("Soldier", healthHP(Entity.Entry(type: .Soldier, x: 10, y: 10, hp: 79)))
print("Player", healthHP(Entity.Entry(type: .Player, x: 10, y: 10, hp: 57)))
// Prints:
"Soldier 0"
"Player 43"
This is a beautiful example of the culmination of the various mechanisms we've discussed so far.
It is very clear, there is no nesting involved
Logic and initialization of state are handled at the top of the func which improves readability
Very terse.
This can also be very successfully combined with switch and for to wrap complex logical constructs into an easy to read format. Of course, that won't make the logic any easier to understand, but at least it will be provided in a much saner package. Especially if you use enums.
8 Using if case
if case can be used as the opposite of guard case. It is a great way to unwrap and match data within a branch. In line with our previous guard example. Obviously, we need an move function. Something that allows us to say that an entity moved in a direction. Since our entities are enums, we need to return an updated entity.
func move(entity: Entity, xd: Int, yd: Int) -> Entity {
if case Entity.Entry(let t, let x, let y, let hp) = entity
where (x + xd) < 1000 &&
(y + yd) < 1000 {
return Entity.Entry(type: t, x: (x + xd), y: (y + yd), hp: hp)
}
return entity
}
print(move(Entity.Entry(type: .Soldier, x: 10, y: 10, hp: 79), xd: 30, yd: 500))
// prints: Entry(main.Entity.EntityType.Soldier, 40, 510, 79)
9 Limitations
Some limitations were already mentioned in the text, such as the issues regarding Expression Patterns, which seem to not match against tuples (as would be really convenient). In Scala or Clojure, pattern matching can also work against collections, so you could match head, tail, parts, etc. 4 This doesn't work in Swift (although Austin Zheng kinda implemented this in the blog post I linked above).
Another thing which doesn't work (wich, again, Scala does just fine) is destructuring against classes or structs. Scala allows us to define an unapply method which does basically the opposite of init. Implementing this method, then, allows the type checker to match against classes. In Swift, this could look as follows:
struct Imaginary {
let x: Int
let y: Int
func unapply() -> (Int, Int) {
// implementing this method would then in theory provide all the details needed to destructure the vars
return (self.x, self.y)
}
}
// this, then, would unapply automatically and then match
guard case let Imaginary(x, y) = anImaginaryObject else { break }
All patterns work for all three keywords. Changed that, and added a Gist with examples
The limitations regarding protocols and the expression pattern were invalid. This works fine, too.
Added "Pattern Availability" section
08/24/2015
Added if case examples, renamed some sections.
Fixed typos in the text. In particular, I accidentally wrote that _ does not match nil. That's of course not true, _ matches everything. (thanks to obecker)
I'm not sure whether the compiler optimizes for this, but theoretically, it should be able to calculate the correct position of the requested data and inline the address ignoring the other parts of the enum case
{:description
"In this post, we'll have a look at Pattern Matching in Swift in terms of the 'switch', 'for', 'if', and 'guard' keywords. We'll have a look at the basic syntax and at best practices and helpful examples.",
:keyword-tags (:swift :ios :cocoa),
:projects ({:project "Sarbatka", :link "/electronic-music.html"}),
:postlist
({:title "Blogstrapped.",
:url "/2011/12/01/blogstrapped/",
:tags "entrepeneurship blog",
:keyword-tags (:entrepeneurship :blog),
:date "Thu, 1 Dec 2011",
:keywords "entrepeneurship videro fear unknown stylemac",
:keyword-keywords
(:entrepeneurship :videro :fear :unknown :stylemac)}
{:title "Fast NSDictionary traversal in Objective-C",
:url "/2011/12/07/fast-nsdictionary-traversal-in-objective-c/",
:tags "objective-c ios cocoa",
:keyword-tags (:objective-c :ios :cocoa),
:date "Wed, 7 Dec 2011"}
{:title "How the iPad can improve focus",
:url "/2011/12/09/how-the-ipad-can-improve-focus/",
:tags "opinion",
:keyword-tags (:opinion),
:date "Fri, 9 Dec 2011"}
{:title "Use VIM as an Xcode alternative",
:url "/2013/01/29/use-vim-as-xcode-alternative-ios-mac-cocoa/",
:tags "cocoa objective-c ios",
:keyword-tags (:cocoa :objective-c :ios),
:date "Tue, 29 Jan 2013"}
{:title "Now Running Clojure",
:url "/2014/01/20/now-running-clojure/",
:tags "clojure blog",
:keyword-tags (:clojure :blog),
:date "Mon, 20 Jan 2014"}
{:title
"Debugging entitlement issues in Maps, iCloud, In-App, Keychain, or GameCenter",
:url
"/2014/01/21/debugging-entitlement-maps-icloud-gamecenter-issues/",
:tags "ios cocoa",
:keyword-tags (:ios :cocoa),
:date "Tue, 21 Jan 2014",
:keywords "ios cocoa entitlements",
:keyword-keywords (:ios :cocoa :entitlements)}
{:title
"Clojure/Enlive Static Site Generator that keeps your HTML intact",
:url
"/2014/01/22/clojure-enlive-static-site-generator-that-keeps-html-intact/",
:tags "blog clojure",
:keyword-tags (:blog :clojure),
:date "Wed, 22 Jan 2014",
:keywords "clojure static site generator jekyll html enlive",
:keyword-keywords
(:clojure :static :site :generator :jekyll :html :enlive)}
{:title "Finding a good URL Partitioning Scheme for PostgreSQL",
:url "/2014/01/24/finding-url-partitioning-scheme-postgres/",
:tags "postgresql clojure",
:keyword-tags (:postgresql :clojure),
:date "Fri, 24 Jan 2014",
:keywords "clojure postgresql partitioning scheme",
:keyword-keywords (:clojure :postgresql :partitioning :scheme)}
{:title "An Emacs Lisp tooling tutorial, writing a bulk mailer",
:url "/2014/01/29/emacs-lisp-tooling-tutorial-writing-bulk-mailer/",
:tags "emacs",
:keyword-tags (:emacs),
:date "Wed, 29 Jan 2014",
:keywords
"emacs lisp bulk mailer tutorial email vim vimscript evil",
:keyword-keywords
(:emacs :lisp :bulk :mailer :tutorial :email :vim :vimscript :evil)}
{:title
"Creating a Swift syntax extension: the Lisp 'cond' function",
:url "/2014/06/08/writing-simple-syntax-extensions-in-swift/",
:tags "swift ios cocoa",
:keyword-tags (:swift :ios :cocoa),
:date "Sun, 8 Jun 2014",
:keywords
"clojure lisp swift cond syntax macro extension cocoa ios feature",
:keyword-keywords
(:clojure
:lisp
:swift
:cond
:syntax
:macro
:extension
:cocoa
:ios
:feature)}
{:title "Swift optionals made simple",
:url "/2014/06/13/swift-optionals-made-simple/",
:tags "swift ios cocoa",
:keyword-tags (:swift :ios :cocoa),
:date "Fri, 13 Jun 2014",
:keywords
"lisp swift optional scala simple optionals switch chaining feature",
:keyword-keywords
(:lisp
:swift
:optional
:scala
:simple
:optionals
:switch
:chaining
:feature)}
{:title "Generic method overloading by protocol in Swift",
:url "/2015/06/17/swift-method-overloading-by-protocol/",
:tags "swift ios cocoa",
:keyword-tags (:swift :ios :cocoa),
:date "Wed, 17 Jun 2015",
:keywords
"swift optional simple overloading method protocol extensions generics feature",
:keyword-keywords
(:swift
:optional
:simple
:overloading
:method
:protocol
:extensions
:generics
:feature)}
{:title "Using try / catch in Swift with asynchronous closures",
:url "/2015/06/19/swift-try-catch-asynchronous-closures/",
:tags "swift ios",
:keyword-tags (:swift :ios),
:date "Fri, 19 Jun 2015",
:keywords "swift try catch errortype closure async result feature",
:keyword-keywords
(:swift :try :catch :errortype :closure :async :result :feature)}
{:title "Debugging advanced compilation errors in ClojureScript",
:url "/2015/07/02/debugging-clojurescript-advanced-compilation/",
:tags "clojure",
:keyword-tags (:clojure),
:date "Thu, 2 Jul 2015",
:keywords "debugging clojure clojurescript externs",
:keyword-keywords (:debugging :clojure :clojurescript :externs)}
{:title "Tuples in Swift, Advanced Usage and Best Practices",
:url "/2015/07/19/tuples-swift-advanced-usage-best-practices/",
:tags "swift",
:keyword-tags (:swift),
:date "Sun, 19 Jul 2015",
:keywords "swift tuples generics feature",
:keyword-keywords (:swift :tuples :generics :feature)}
{:title "Match Me if you can: Swift Pattern Matching in Detail.",
:url "/2015/08/20/swift-pattern-matching-in-detail/",
:tags "swift ios cocoa",
:keyword-tags (:swift :ios :cocoa),
:date "Thu, 20 Aug 2015",
:keywords
"feature lisp swift optional scala simple optionals switch chaining for pattern matching clojure haskell",
:keyword-keywords
(:feature
:lisp
:swift
:optional
:scala
:simple
:optionals
:switch
:chaining
:for
:pattern
:matching
:clojure
:haskell)}
{:title "Optional throw via try? in Swift 2 beta 6",
:url "/2015/08/25/optional-throw-swift/",
:tags "swift",
:keyword-tags (:swift),
:date "Tue, 25 Aug 2015",
:keywords
"swift error throw result either rethrow try syntax swift2",
:keyword-keywords
(:swift
:error
:throw
:result
:either
:rethrow
:try
:syntax
:swift2)}
{:title "Getting your iPhone 6s Chip Foundry from Swift",
:url "/2015/09/30/getting-iphone6s-foundry-from-swift/",
:tags "swift",
:keyword-tags (:swift),
:date "Wed, 30 Sep 2015",
:keywords
"swift iphone6s iphone tsmc samsung gestalt private api foundation",
:keyword-keywords
(:swift
:iphone6s
:iphone
:tsmc
:samsung
:gestalt
:private
:api
:foundation)}
{:title "Advanced & Practical Enum usage in Swift",
:url "/2015/10/17/advanced-practical-enum-examples/",
:tags "swift cocoa ios",
:keyword-tags (:swift :cocoa :ios),
:date "Sat, 17 Oct 2015",
:keywords
"feature swift enum algebraic caseclass union case switch pattern simple practical advanced example",
:keyword-keywords
(:feature
:swift
:enum
:algebraic
:caseclass
:union
:case
:switch
:pattern
:simple
:practical
:advanced
:example)}
{:title "The Swift Reflection API and what you can do with it",
:url "/2015/10/24/swift-reflection-api-what-you-can-do/",
:tags "swift cocoa ios",
:keyword-tags (:swift :cocoa :ios),
:date "Sat, 24 Oct 2015",
:keywords
"feature swift reflection struct class displayType mirror api reflecting any anyobject",
:keyword-keywords
(:feature
:swift
:reflection
:struct
:class
:displayType
:mirror
:api
:reflecting
:any
:anyobject)}
{:title "Reduce all the things",
:url "/2015/11/30/reduce-all-the-things/",
:tags "swift cocoa ios",
:keyword-tags (:swift :cocoa :ios),
:date "Mon, 30 Nov 2015",
:keywords
"feature swift reduce map filter group partition split interpose chunk functional programming flatMap",
:keyword-keywords
(:feature
:swift
:reduce
:map
:filter
:group
:partition
:split
:interpose
:chunk
:functional
:programming
:flatMap)}
{:title
"Swift Package Manager: Create and Use a X11 package on Linux",
:url "/2015/12/08/swift-ubuntu-x11-window-app/",
:tags "swift linux",
:keyword-tags (:swift :linux),
:date "Tue, 8 Dec 2015",
:keywords "linux x11 swift libx11 xserver xorg",
:keyword-keywords (:linux :x11 :swift :libx11 :xserver :xorg)}
{:title "Hirundo: Comfortably follow Swift Mailing Lists on OSX",
:url "/2016/02/02/hirundo-mac-app-swift-mailing-lists/",
:tags "swift cocoa ios",
:keyword-tags (:swift :cocoa :ios),
:date "Tue, 2 Feb 2016",
:keywords
"swift mac cocoa mailing list swift-dev swift-eveolution swift-users reading macosx",
:keyword-keywords
(:swift
:mac
:cocoa
:mailing
:list
:swift-dev
:swift-eveolution
:swift-users
:reading
:macosx)}
{:title "Three tips for concise Swift using the Guard statement",
:url "/2016/03/29/three-tips-for-clean-swift-code/",
:tags "swift cocoa ios",
:keyword-tags (:swift :cocoa :ios),
:date "Tue, 29 Mar 2016",
:keywords
"swift mac cocoa guard let enum pattern matching patterns",
:keyword-keywords
(:swift :mac :cocoa :guard :let :enum :pattern :matching :patterns)}
{:title "Using Git Hooks to prevent commiting test code",
:url "/2016/04/04/prevent-accidental-test-code-commits/",
:tags "git",
:keyword-tags (:git),
:date "Mon, 4 Apr 2016",
:keywords "git hook commit debug test code",
:keyword-keywords (:git :hook :commit :debug :test :code)}
{:title
"Force optionals in multi-unwrapped \"guard let\" or \"if let\"",
:url
"/2016/04/14/force-optionals-in-guard-or-let-optional-binding/",
:tags "swift cocoa ios",
:keyword-tags (:swift :cocoa :ios),
:date "Thu, 14 Apr 2016",
:keywords
"swift guard let unwrap bind binding unwrapped optional some none optionals",
:keyword-keywords
(:swift
:guard
:let
:unwrap
:bind
:binding
:unwrapped
:optional
:some
:none
:optionals)}
{:title "Raw value initializers for enums with associated types",
:url "/2016/04/23/associated-types-enum-raw-value-initializers/",
:tags "swift cocoa ios",
:keyword-tags (:swift :cocoa :ios),
:date "Sat, 23 Apr 2016",
:keywords
"swift optional enum raw value initializers associated type",
:keyword-keywords
(:swift
:optional
:enum
:raw
:value
:initializers
:associated
:type)}
{:title "SwiftWatch",
:url "/2016/04/28/swiftwatch/",
:tags "swift cocoa ios",
:keyword-tags (:swift :cocoa :ios),
:date "Thu, 28 Apr 2016",
:keywords
"swift hackernews reddit designernews lamernews socialnews swiftlang programming community post vote comment",
:keyword-keywords
(:swift
:hackernews
:reddit
:designernews
:lamernews
:socialnews
:swiftlang
:programming
:community
:post
:vote
:comment)}
{:title "Data in Swift 3 parsing a Doom WAD File",
:url "/2016/07/15/swift3-nsdata-data/",
:tags "swift cocoa ios",
:keyword-tags (:swift :cocoa :ios),
:date "Fri, 15 Jul 2016",
:keywords "swift doom wad lumps data nsdata swift3 binary bytes",
:keyword-keywords
(:swift :doom :wad :lumps :data :nsdata :swift3 :binary :bytes)}),
:tags
"benedikt, c, chaining, clojure, clojurescript, cocoa, feature, for, haskell, html, ios, javascript, lisp, mac, matching, objective-c, optional, optionals, pattern, photodesk, research, scala, simple, stylemac, swift, switch, terhechte",
:type :post,
:keywords
"feature lisp swift optional scala simple optionals switch chaining for pattern matching clojure haskell",
:title "Match Me if you can: Swift Pattern Matching in Detail.",
:author "Benedikt Terhechte",
:feature-image
"/img-content/2015-08-20-swift-pattern-matching-in-detail-feature-image.jpg",
:categories
({:tag "blog", :url "/tags/blog/index.html", :count 3}
{:tag "clojure", :url "/tags/clojure/index.html", :count 4}
{:tag "cocoa", :url "/tags/cocoa/index.html", :count 16}
{:tag "emacs", :url "/tags/emacs/index.html", :count 1}
{:tag "entrepeneurship",
:url "/tags/entrepeneurship/index.html",
:count 1}
{:tag "git", :url "/tags/git/index.html", :count 1}
{:tag "ios", :url "/tags/ios/index.html", :count 17}
{:tag "linux", :url "/tags/linux/index.html", :count 1}
{:tag "objective-c", :url "/tags/objective-c/index.html", :count 2}
{:tag "opinion", :url "/tags/opinion/index.html", :count 1}
{:tag "postgresql", :url "/tags/postgresql/index.html", :count 1}
{:tag "swift", :url "/tags/swift/index.html", :count 18}),
:url "/2015/08/20/swift-pattern-matching-in-detail/",
:blog-index nil,
:watching nil,
:site-title "Appventure",
:keyword-keywords
(:feature
:lisp
:swift
:optional
:scala
:simple
:optionals
:switch
:chaining
:for
:pattern
:matching
:clojure
:haskell)}
[{:keyword-tags (:swift :ios :cocoa),
:tags "swift ios cocoa",
:date "Thu, 20 Aug 2015",
:footnotes nil,
:meta
{:feature-image
"/img-content/2015-08-20-swift-pattern-matching-in-detail-feature-image.jpg",
:title "Match Me if you can: Swift Pattern Matching in Detail.",
:keyword-tags (:swift :ios :cocoa),
:tags "swift ios cocoa",
:keyword-keywords
(:feature
:lisp
:swift
:optional
:scala
:simple
:optionals
:switch
:chaining
:for
:pattern
:matching
:clojure
:haskell),
:keywords
"feature lisp swift optional scala simple optionals switch chaining for pattern matching clojure haskell",
:description
"In this post, we'll have a look at Pattern Matching in Swift in terms of the 'switch', 'for', 'if', and 'guard' keywords. We'll have a look at the basic syntax and at best practices and helpful examples."},
:content
"<!-- #+feature-image: /img-content/2015-08-20-swift-pattern-matching-in-detail-feature-image.jpg -->\n\n<div id=\"table-of-contents\">\n<h2>Table of Contents</h2>\n<div id=\"text-table-of-contents\">\n<ul>\n<li><a href=\"#sec-1\">1. Diving In</a></li>\n<li><a href=\"#sec-2\">2. A Trading Engine</a>\n<ul>\n<li><a href=\"#sec-2-1\">2.1. First Draft</a></li>\n<li><a href=\"#sec-2-2\">2.2. Trader Types</a></li>\n<li><a href=\"#sec-2-3\">2.3. Guards! Guards!</a></li>\n</ul>\n</li>\n<li><a href=\"#sec-3\">3. Advanced Pattern Matching</a>\n<ul>\n<li><a href=\"#sec-3-1\">3.1. 1. Wildcard Pattern</a></li>\n<li><a href=\"#sec-3-2\">3.2. 2. Identifier Pattern</a></li>\n<li><a href=\"#sec-3-3\">3.3. 3. Value-Binding Pattern</a></li>\n<li><a href=\"#sec-3-4\">3.4. 4. Tuple Pattern</a></li>\n<li><a href=\"#sec-3-5\">3.5. 5. Enumeration Case Pattern</a></li>\n<li><a href=\"#sec-3-6\">3.6. 6. Type-Casting Patterns</a></li>\n<li><a href=\"#sec-3-7\">3.7. 7. Expression Pattern</a></li>\n<li><a href=\"#sec-3-8\">3.8. Fallthrough, Break, and Labels</a></li>\n</ul>\n</li>\n<li><a href=\"#sec-4\">4. Real World Examples</a>\n<ul>\n<li><a href=\"#sec-4-1\">4.1. Optionals</a></li>\n<li><a href=\"#sec-4-2\">4.2. Type Matches</a></li>\n<li><a href=\"#sec-4-3\">4.3. Applying ranges for grading</a></li>\n<li><a href=\"#sec-4-4\">4.4. Word Frequencies</a></li>\n<li><a href=\"#sec-4-5\">4.5. Directory Traversion</a></li>\n<li><a href=\"#sec-4-6\">4.6. Fibonacci</a></li>\n<li><a href=\"#sec-4-7\">4.7. Legacy API and Value Extractions</a></li>\n</ul>\n</li>\n<li><a href=\"#sec-5\">5. Patterns with other Keywords</a></li>\n<li><a href=\"#sec-6\">6. Using <b>for case</b></a></li>\n<li><a href=\"#sec-7\">7. Using <b>guard case</b></a></li>\n<li><a href=\"#sec-8\">8. Using <b>if case</b></a></li>\n<li><a href=\"#sec-9\">9. Limitations</a></li>\n<li><a href=\"#sec-10\">10. Changes</a></li>\n</ul>\n</div>\n</div>\n<h6><a href=\"http://swift.gg/2015/10/27/swift-pattern-matching-in-detail/\">This post is also available in <b>🇨🇳Chinese</b></a><span> Thanks to </span><a href=\"http://swift.gg/tags/APPVENTURE/\">SwiftGG</a></h6>\n<h6><a href=\"http://qiita.com/mono0926/items/f2875a9eacef53e88122\">This post is also available in <b>🇯🇵Japanese</b></a><span> Thanks to </span><a href=\"https://twitter.com/_mono\">M Ono</a></h6>\n\n<p>\nAmong the new features that Swift offers to Objective-C programmers is one that disguises itself like a boring old man while it offers huge potential for forming elegant solutions to otherwise unwieldy sets of nested branches. I'm, of course talking about the <code>switch</code> statement that many Objective-C programmers probably consider as a clunky syntax device which is most entertaining when used as <a href=\"http://en.wikipedia.org/wiki/Duff's_device\">Duff's Device</a>, yet usually offers little to no advantages over multiple if statements.\n</p>\n\n<p>\nThe <code>Switch</code> statement in Swift can do much more though. In the following tutorial, I will try to explain the various usages for these new features in more detail. I'll mostly ignore those solutions where there's no benefit over how <code>switch</code> works in Objective-C or C. The basics of this post were actually written in July 2014, but so many of my patterns crashed the compiler back then that I postponed writing it until there's better support.\n</p>\n\n<p>\nThis Blog Post is also available in the following languages:\n</p>\n\n<div id=\"outline-container-sec-1\" class=\"outline-2\">\n<h2 id=\"sec-1\"><span class=\"section-number-2\">1</span> Diving In</h2>\n<div class=\"outline-text-2\" id=\"text-1\">\n<p>\nThe main feature of <code>switch</code> is of course pattern matching, the ability to destructure values and match different switch cases based on correct match of the values to the cases. \n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-Swift\">// Example of the worst binary -> decimal converter in history\nlet bool1 = 1\nlet bool2 = 0\nswitch (bool1, bool2) {\n case (0, 0): print(\"0\")\n case (0, 1): print(\"1\")\n case (1, 0): print(\"2\")\n case (1, 1): print(\"3\")\n}\n</pre>\n</div>\n\n<p>\nPattern matching has long existed in other languages like Haskell, Erlang, Scala, or Prolog. This is a boon, because it allows us to have a look at how those languages utilize pattern matching in order to solve their problems. We can even have a look at their examples to find the most practical ones that offer real world adaptability.\n</p>\n</div>\n</div>\n\n<div id=\"outline-container-sec-2\" class=\"outline-2\">\n<h2 id=\"sec-2\"><span class=\"section-number-2\">2</span> A Trading Engine</h2>\n<div class=\"outline-text-2\" id=\"text-2\">\n<p>\nSo Wall Street contacted you, they need a new trading platform running on iOS devices. As it is a trading platform, you define an <code>enum</code> for trades.\n</p>\n</div>\n\n<div id=\"outline-container-sec-2-1\" class=\"outline-3\">\n<h3 id=\"sec-2-1\"><span class=\"section-number-3\">2.1</span> First Draft</h3>\n<div class=\"outline-text-3\" id=\"text-2-1\">\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">enum Trades {\n case Buy(stock: String, amount: Int, stockPrice: Float)\n case Sell(stock: String, amount: Int, stockPrice: Float)\n}\n</pre>\n</div>\n\n<p>\nYou were also handed the following API to handle trades. <b>Notice how sell orders are just negative amounts</b>. And you're told the stock price is not important, their engine will take an internal one anyway.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">/**\n - parameter stock: The stock name\n - parameter amount: The amount, negative number = sell, positive = buy\n*/\nfunc process(stock: String, _ amount: Int) {\n print (\"\\(amount) of \\(stock)\")\n}\n</pre>\n</div>\n\n<p>\nThe next step is to process those trades. You see the potential for using pattern matching and write this:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let aTrade = Trades.Buy(stock: \"APPL\", amount: 200, stockPrice: 115.5)\n\nswitch aTrade {\ncase .Buy(let stock, let amount, _):\n process(stock, amount)\ncase .Sell(let stock, let amount, _):\n process(stock, amount * -1)\n}\n// Prints \"buy 200 of APPL\"\n</pre>\n</div>\n\n<p>\nSwift lets us conveniently only destructure / extract the information from the <code>enum</code> that we really want. In this case only the stock and the amount.\n</p>\n\n<p>\nAwesome, you visit Wall Street to show of your fantastic trading platform. However, as always, the reality is much more cumbersome than the beautiful theory. Trades aren't trades you learn. \n</p>\n\n<ul class=\"org-ul\">\n<li>You have to calculate in a fee which is different based on the trader type. \n</li>\n<li>The smaller the institution the higher the fee. \n</li>\n<li>Also, bigger institutions get a higher priority. \n</li>\n</ul>\n\n<p>\nThey also realized that you'll need a new API for this, so you were handed this:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">func processSlow(stock: String, _ amount: Int, _ fee: Float) { print(\"slow\") }\nfunc processFast(stock: String, _ amount: Int, _ fee: Float) { print(\"fast\") }\n</pre>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-2-2\" class=\"outline-3\">\n<h3 id=\"sec-2-2\"><span class=\"section-number-3\">2.2</span> Trader Types</h3>\n<div class=\"outline-text-3\" id=\"text-2-2\">\n<p>\nSo you go back to the drawing board and add another <code>enum</code>. The trader type is part of every trade, too.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">enum TraderType {\ncase SingleGuy\ncase Company\n} \n\nenum Trades {\n case Buy(stock: String, amount: Int, stockPrice: Float, type: TraderType)\n case Sell(stock: String, amount: Int, stockPrice: Float, type: TraderType)\n}\n</pre>\n</div>\n\n<p>\nSo, how do you best implement this new restriction? You could just have an <code>if</code> / <code>else</code> switch for buy and for sell, but that would lead to nested code which quickly lacks clarity - and who knows maybe these Wall Street guys come up with further complications. So you define it instead as additional requirements on the pattern matches:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let aTrade = Trades.Sell(stock: \"GOOG\", amount: 100, stockPrice: 666.0, type: TraderType.Company)\n\nswitch aTrade {\ncase let .Buy(stock, amount, _, TraderType.SingleGuy):\n processSlow(stock, amount, 5.0)\ncase let .Sell(stock, amount, _, TraderType.SingleGuy):\n processSlow(stock, -1 * amount, 5.0)\ncase let .Buy(stock, amount, _, TraderType.Company):\n processFast(stock, amount, 2.0)\ncase let .Sell(stock, amount, _, TraderType.Company):\n processFast(stock, -1 * amount, 2.0)\n}\n</pre>\n</div>\n\n<p>\nThe beauty of this is that there's a very succinct flow describing the different possible combinations.\nAlso, note how we changed <code>.Buy(let stock, let amount)</code> into <code>let .Buy(stock, amount)</code> in order to keep things simpler. This will destructure the <code>enum</code> just as before, only with less syntax.\n</p>\n</div>\n</div>\n\n<div id=\"outline-container-sec-2-3\" class=\"outline-3\">\n<h3 id=\"sec-2-3\"><span class=\"section-number-3\">2.3</span> Guards! Guards!</h3>\n<div class=\"outline-text-3\" id=\"text-2-3\">\n<p>\nOnce again you present your development to your Wall Street customer, and once again a new issue pops up (you really should have asked for a more detailed project description). \n</p>\n\n<ul class=\"org-ul\">\n<li>Sell orders exceeding a total value of $1.000.000 do always get fast handling, even if it's just a single guy. \n</li>\n<li>Buy orders under a total value of $1.000 do always get slow handling.\n</li>\n</ul>\n\n<p>\nWith traditional nested <code>if</code> syntax, this would already become a bit messy. Not so with <code>switch</code>. Swift includes guards for <code>switch cases</code> which allow you to further restrict the possible matching of those cases. \n</p>\n\n<p>\nYou only need to modify your <code>switch</code> a little bit to accommodate for those new changes\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let aTrade = Trades.Buy(stock: \"GOOG\", amount: 1000, stockPrice: 666.0, type: TraderType.SingleGuy)\n\nswitch aTrade {\ncase let .Buy(stock, amount, _, TraderType.SingleGuy):\n processSlow(stock, amount, 5.0)\ncase let .Sell(stock, amount, price, TraderType.SingleGuy)\n where price*Float(amount) > 1000000:\n processFast(stock, -1 * amount, 5.0)\ncase let .Sell(stock, amount, _, TraderType.SingleGuy):\n processSlow(stock, -1 * amount, 5.0)\ncase let .Buy(stock, amount, price, TraderType.Company)\n where price*Float(amount) < 1000:\n processSlow(stock, amount, 2.0)\ncase let .Buy(stock, amount, _, TraderType.Company):\n processFast(stock, amount, 2.0)\ncase let .Sell(stock, amount, _, TraderType.Company):\n processFast(stock, -1 * amount, 2.0)\n}\n</pre>\n</div>\n\n<p>\nThis code is quite structured, still rather easy to read, and wraps up the complex cases quite well.\n</p>\n\n<p>\nThat's it, we've successfully implemented our trading engine. However, this solution still has a bit of repetition; we wonder if there're pattern matching ways to improve upon that. So, let's look into pattern matching a bit more.\n</p>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-3\" class=\"outline-2\">\n<h2 id=\"sec-3\"><span class=\"section-number-2\">3</span> Advanced Pattern Matching</h2>\n<div class=\"outline-text-2\" id=\"text-3\">\n<p>\nSo now we've seen several patterns in action. But what's the syntax here? Which other things can we match for? Swift distinguishes <b>7</b> different patterns. We're going to have a quick look at each of them.\n</p>\n\n<p>\nAll of those patterns can not only be used with the <code>switch</code> keyword, but also with the <code>if</code>, <code>guard</code>, and <code>for</code> keywords. For details on this, see below.\n</p>\n</div>\n\n<div id=\"outline-container-sec-3-1\" class=\"outline-3\">\n<h3 id=\"sec-3-1\"><span class=\"section-number-3\">3.1</span> 1. Wildcard Pattern</h3>\n<div class=\"outline-text-3\" id=\"text-3-1\">\n<p>\nThe wildcard pattern ignores the value to be matched against. In this case any value is possible. This is the same pattern as <code>let _ = fn()</code> where the <code>_</code> indicates that you don't wish to further use this value. The interesting part is that this matches all values including <code>nil</code> <sup><a id=\"fnr.1\" name=\"fnr.1\" class=\"footref\" href=\"#fn.1\">1</a></sup>. You can even match optionals by appending a <code>?</code>:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let p: String? = nil\nswitch p {\ncase _?: print (\"Has String\")\ncase nil: print (\"No String\")\n}\n</pre>\n</div>\n\n<p>\nAs you've seen in the trading example, it also allows you to omit the data you don't need from matching <code>enums</code> or <code>tuples</code>:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">switch (15, \"example\", 3.14) {\n case (_, _, let pi): print (\"pi: \\(pi)\")\n}\n</pre>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-3-2\" class=\"outline-3\">\n<h3 id=\"sec-3-2\"><span class=\"section-number-3\">3.2</span> 2. Identifier Pattern</h3>\n<div class=\"outline-text-3\" id=\"text-3-2\">\n<p>\nMatches a concrete value. This is how things work in Objective-C's <code>switch</code> implementation:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">switch 5 {\n case 5: print(\"5\")\n}\n</pre>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-3-3\" class=\"outline-3\">\n<h3 id=\"sec-3-3\"><span class=\"section-number-3\">3.3</span> 3. Value-Binding Pattern</h3>\n<div class=\"outline-text-3\" id=\"text-3-3\">\n<p>\nThis is the very same as binding values to variables via <code>let</code> or <code>var</code>. Only in a switch statement. You've already seen this before, so I'll provide a very short example:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">switch (4, 5) {\n case let (x, y): print(\"\\(x) \\(y)\")\n}\n</pre>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-3-4\" class=\"outline-3\">\n<h3 id=\"sec-3-4\"><span class=\"section-number-3\">3.4</span> 4. Tuple Pattern</h3>\n<div class=\"outline-text-3\" id=\"text-3-4\">\n<p>\n<a href=\"http://appventure.me/2015/07/19/tuples-swift-advanced-usage-best-practices/\">I've written a whole blog post about tuples,</a> which offer much more information than this, but here's a quick example:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let age = 23\nlet job: String? = \"Operator\"\nlet payload: AnyObject = NSDictionary()\n\nswitch (age, job, payload) {\n case (let age, _?, _ as NSDictionary):\n print(age)\n default: ()\n}\n</pre>\n</div>\n\n<p>\nHere, we're combining three values into a tuple (imagine they're coming from different API calls) and matching them in one go. Note that the pattern achieves three things:\n</p>\n<ol class=\"org-ol\">\n<li>It extracts the age\n</li>\n<li>It makes sure there is a job, even though we don't need it\n</li>\n<li>It makes sure that the payload is of kind <code>NSDictionary</code> even though we don't need the actual value either.\n</li>\n</ol>\n</div>\n</div>\n\n<div id=\"outline-container-sec-3-5\" class=\"outline-3\">\n<h3 id=\"sec-3-5\"><span class=\"section-number-3\">3.5</span> 5. Enumeration Case Pattern</h3>\n<div class=\"outline-text-3\" id=\"text-3-5\">\n<p>\nAs you saw in our trading example, pattern matching works <b>really great</b> with Swift's <code>enums</code>. That's because <code>enum cases</code> are like sealed, immutable, destructable structs. Much like with <code>tuples</code>, you can unwrap the contents of an individual case right in the match and only extract the information you need <sup><a id=\"fnr.2\" name=\"fnr.2\" class=\"footref\" href=\"#fn.2\">2</a></sup>.\n</p>\n\n<p>\nImagine you're writing a game in a functional style and you have a couple of entities that you need to define. You could use <code>structs</code> but as your entities will have very little state, you feel that that's a bit of an overkill.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">enum Entities {\n case Soldier(x: Int, y: Int)\n case Tank(x: Int, y: Int)\n case Player(x: Int, y: Int)\n}\n</pre>\n</div>\n\n<p>\nNow you need to implement the drawing loop. Here, we only need the X and Y position:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">for e in entities() {\n switch e {\n case let .Soldier(x, y):\n drawImage(\"soldier.png\", x, y)\n case let .Tank(x, y):\n drawImage(\"tank.png\", x, y)\n case let .Player(x, y):\n drawImage(\"player.png\", x, y)\n }\n}\n</pre>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-3-6\" class=\"outline-3\">\n<h3 id=\"sec-3-6\"><span class=\"section-number-3\">3.6</span> 6. Type-Casting Patterns</h3>\n<div class=\"outline-text-3\" id=\"text-3-6\">\n<p>\nAs the name already implies, this pattern casts or matches types. It has two different keywords:\n</p>\n\n<ul class=\"org-ul\">\n<li><code>is</code> <b>type</b>: Matches the runtime type (or a subclass of it) against the right hand side. This performs a type cast but disregards the returned type. So your <code>case</code> block won't know about the matched type.\n</li>\n<li>pattern <code>as</code> <b>type</b>: Performs the same match as the <code>is</code> pattern but for a successful match casts the type into the pattern specified on the left hand side.\n</li>\n</ul>\n\n<p>\nHere is an example of the two. \n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let a: Any = 5 \nswitch a {\n // this fails because a is still anyobject\n // error: binary operator '+' cannot be applied to operands of type 'Any' and 'Int'\n case is Int: print (a + 1)\n // This works and returns '6'\n case let n as Int: print (n + 1)\n default: ()\n}\n</pre>\n</div>\n\n<p>\nNote that there is no <code>pattern</code> before the <code>is</code>. It matches directly against <code>a</code>.\n</p>\n</div>\n</div>\n\n<div id=\"outline-container-sec-3-7\" class=\"outline-3\">\n<h3 id=\"sec-3-7\"><span class=\"section-number-3\">3.7</span> 7. Expression Pattern</h3>\n<div class=\"outline-text-3\" id=\"text-3-7\">\n<p>\nThe expression pattern is very powerful. It matches the <code>switch</code> value against an expression implementing the <code>~=</code> operator. There're default implementations for this operator, for example for ranges, so that you can do:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">switch 5 {\n case 0..10: print(\"In range 0-10\")\n}\n</pre>\n</div>\n\n<p>\nHowever, the much more interesting possibility is overloading the operator yourself in order to add matchability to your custom types. Let's say that you decided to rewrite the soldier game we wrote earlier and you want to use structs after all.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">struct Soldier {\n let hp: Int\n let x: Int\n let y: Int\n}\n</pre>\n</div>\n\n<p>\nNow you'd like to easily match against all entities with a health of <b>0</b>. We can simply implement the <code>~=</code> operators as follows.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">func ~= (pattern: Int, value: Soldier) -> Bool {\n return pattern == value.hp\n}\n</pre>\n</div>\n\n<p>\nNow we can match against an entity:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let soldier = Soldier(hp: 99, x: 10, y: 10)\nswitch soldier {\n case 0: print(\"dead soldier\")\n default: ()\n}\n</pre>\n</div>\n\n<p>\nSadly, full matching with tuples does not seem to work. If you implement the code below, there'll be a type checker error.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">func ~= (pattern: (hp: Int, x: Int, y: Int), value: Soldier) -> Bool {\n let (hp, x, y) = pattern\n return hp == value.hp && x == value.x && y == value.y\n}\n</pre>\n</div>\n\n<p>\nOne possible way of implementing something akin to the above is by adding a <code>unapply</code> method to your <code>struct</code> and then matching against that:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">extension Soldier {\n func unapply() -> (Int, Int, Int) {\n return (self.hp, self.x, self.y)\n }\n}\n\nfunc ~= (p: (Int, Int, Int), t: (Int, Int, Int)) -> Bool {\n return p.0 == t.0 && p.1 == t.1 && p.2 == t.2 \n}\n\nlet soldier = Soldier(hp: 99, x: 10, y: 10)\nprint(soldier.unapply() ~= (99, 10, 10))\n</pre>\n</div>\n\n<p>\nBut this is rather cumbersome and defeats the purpose of a lot of the magic behind pattern matching.\n</p>\n\n<p>\nIn an earlier version of this post, I wrote that <code>~=</code> doesn't work with protocols, but I was wrong. I remember that I tried it in a Playground, and it didn't work. However, this example (<a href=\"https://www.reddit.com/r/swift/comments/3hq6id/match_me_if_you_can_swift_pattern_matching_in/cub187r\">as kindly provided by latrodectus on reddit</a>) does work fine:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">protocol Entity {\n var value: Int {get}\n}\n\nstruct Tank: Entity {\n var value: Int\n init(_ value: Int) { self.value = value }\n}\n\nstruct Peasant: Entity {\n var value: Int\n init(_ value: Int) { self.value = value }\n}\n\nfunc ~=(pattern: Entity, x: Entity) -> Bool {\n return pattern.value == x.value\n}\n\nswitch Tank(42) {\n case Peasant(42): print(\"Matched\") // Does match\n default: ()\n}\n</pre>\n</div>\n\n<p>\nThere's a lot of things you can do with <code>Expression Patterns</code>. For a much more detailed explanation of Expression Patterns, <a href=\"http://austinzheng.com/2014/12/17/custom-pattern-matching/\">have a look at this terrific blog post by Austin Zheng</a>.\n</p>\n\n<p>\nThis completes list of possible switch patterns. Before we move on, there's one final thing to discuss.\n</p>\n</div>\n</div>\n\n<div id=\"outline-container-sec-3-8\" class=\"outline-3\">\n<h3 id=\"sec-3-8\"><span class=\"section-number-3\">3.8</span> Fallthrough, Break, and Labels</h3>\n<div class=\"outline-text-3\" id=\"text-3-8\">\n<p>\nThe following is not directly related to pattern matching but only affects the <code>switch</code> keyword, so I'll keep it brief. By default, and unlike C/C++/Objective-C, <code>switch</code> <code>cases</code> do not fall through into the next case which is why in Swift, you don't need to write <code>break</code> for every case. You can opt into traditional fallthrough behaviour with the <code>fallthrough</code> keyword.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">switch 5 {\n case 5:\n print(\"Is 5\")\n fallthrough\n default:\n print(\"Is a number\")\n}\n// Will print: \"Is 5\" \"Is a number\"\n</pre>\n</div>\n\n<p>\nAlternatively, you can use <code>break</code> to break out of a switch statement early. Why would you do that if there's no default fallthrough? For example if you can only realize within the <code>case</code> that a certain requirement is not met and you can't execute the <code>case</code> any further:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let userType = \"system\"\nlet userID = 10\nswitch (userType, userID) {\n case (\"system\", _):\n guard let userData = getSystemUser(userID) else { break }\n print(\"user info: \\(userData)\")\n insertIntoRemoteDB(userData)\n default: ()\n}\n... more code that needs to be executed\n</pre>\n</div>\n\n<p>\nHere, we don't want to call <code>insertIntoRemoteData</code> when the result from <code>getSystemUser</code> is <code>nil</code>. Of course, you could just use an <code>if let</code> here, but if multiple of those cases come together, you quickly end up with a bunch of horrifyingly ugly nested <code>if lets</code>. \n</p>\n\n<p>\nBut what if you execute your switch in a <code>while</code> loop and you want to break out of the loop, not the <code>switch</code>? For those cases, Swift allows you to define <code>labels</code> to <code>break</code> or <code>continue</code> to:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">gameLoop: while true {\n switch state() {\n case .Waiting: continue gameLoop\n case .Done: calculateNextState()\n case .GameOver: break gameLoop\n }\n}\n</pre>\n</div>\n\n<p>\nWe've discussed the syntax and implementation details of <code>switch</code> and pattern matching.\nNow, let us have a look at some interesting (more or less) real world examples.\n</p>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-4\" class=\"outline-2\">\n<h2 id=\"sec-4\"><span class=\"section-number-2\">4</span> Real World Examples</h2>\n<div class=\"outline-text-2\" id=\"text-4\">\n</div><div id=\"outline-container-sec-4-1\" class=\"outline-3\">\n<h3 id=\"sec-4-1\"><span class=\"section-number-3\">4.1</span> Optionals</h3>\n<div class=\"outline-text-3\" id=\"text-4-1\">\n<p>\n<a href=\"http://appventure.me/2014/06/13/swift-optionals-made-simple/\">There're many ways to unwrap optionals,</a> and pattern matching is one of them. You've probably used that quite frequently by now, nevertheless, here's a short example:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">var result: String? = secretMethod()\nswitch result {\ncase .None:\n println(\"is nothing\")\ncase let a:\n println(\"\\(a) is a value\")\n}\n</pre>\n</div>\n\n<p>\nWith Swift 2.0, this becomes even easier:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">var result: String? = secretMethod()\nswitch result {\ncase nil:\n print(\"is nothing\")\ncase let a?:\n print(\"\\(a) is a value\")\n}\n</pre>\n</div>\n\n<p>\nAs you can see, <code>result</code> could be a string, but it could also be <code>nil</code>. It's an <code>optional</code>. By switching on result, we can figure out whether it is <code>.None</code> or whether it is an actual value. Even more, if it is a value, we can also bind this value to variable right away. In this case <code>a</code>. What's beautiful here, is the clearly visible distinction between the two states, that the variable <code>result</code> can be in.\n</p>\n</div>\n</div>\n\n<div id=\"outline-container-sec-4-2\" class=\"outline-3\">\n<h3 id=\"sec-4-2\"><span class=\"section-number-3\">4.2</span> Type Matches</h3>\n<div class=\"outline-text-3\" id=\"text-4-2\">\n<p>\nGiven Swift's strong type system, there's usually no need for runtime type checks like it more often happens in Objective-C. However, when you interact with legacy Objective-C code <a href=\"https://netguru.co/blog/objective-c-generics\">(which hasn't been updated to reflect simple generics yet)</a>, then you often end up with code that needs to check for types. Imagine getting an array of NSStrings and NSNumbers:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let u = NSArray(array: [NSString(string: \"String1\"), NSNumber(int: 20), NSNumber(int: 40)])\n</pre>\n</div>\n\n<p>\nWhen you go through this NSArray, you never know what kind of type you get. However, <code>switch</code> statements allow you to easily test for types here:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">for x in u {\n switch x {\n case _ as NSString:\n\tprint(\"string\")\n case _ as NSNumber:\n\tprint(\"number\")\n default:\n\tprint(\"Unknown types\")\n }\n}\n</pre>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-4-3\" class=\"outline-3\">\n<h3 id=\"sec-4-3\"><span class=\"section-number-3\">4.3</span> Applying ranges for grading</h3>\n<div class=\"outline-text-3\" id=\"text-4-3\">\n<p>\nSo you're writing the grading iOS app for your local Highschool. The teachers want to enter a number value from 0 to 100 and receive the grade character for it (A - F). Pattern Matching to the rescue:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let aGrade = 84\n\nswitch aGrade {\ncase 90...100: print(\"A\")\ncase 80...90: print(\"B\")\ncase 70...80: print(\"C\")\ncase 60...70: print(\"D\")\ncase 0...60: print(\"F\")\ndefault:\n print(\"Incorrect Grade\")\n}\n</pre>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-4-4\" class=\"outline-3\">\n<h3 id=\"sec-4-4\"><span class=\"section-number-3\">4.4</span> Word Frequencies</h3>\n<div class=\"outline-text-3\" id=\"text-4-4\">\n<p>\nWe have a sequence of pairs, each representing a word and its frequency in some text. Our goal is to filter out those pairs whose frequency is below or above a certain threshold, and then only return the remaining words, without their respective frequencies. \n</p>\n\n<p>\nHere're our words:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let wordFreqs = [(\"k\", 5), (\"a\", 7), (\"b\", 3)]\n</pre>\n</div>\n\n<p>\nA simple solution would be to model this with <code>map</code> and <code>filter</code>:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let res = wordFreqs.filter({ (e) -> Bool in\n if e.1 > 3 {\n\treturn true\n } else {\n\treturn false\n }\n}).map { $0.0 }\nprint(res)\n</pre>\n</div>\n\n<p>\nHowever, with <code>flatmap</code> a map that only returns the non-nil elements, we can improve a lot upon this solution. First and foremost, we can get rid of the <code>e.1</code> and instead have proper destructuring by utilizing (you guessed it) tuples. And then, we only need one call <code>flatmap</code> instead of <code>filter</code> and then <code>map</code> which adds unnecessary performance overhead.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let res = wordFreqs.flatMap { (e) -> String? in\n switch e {\n case let (s, t) where t > 3: return s\n default: return nil\n }\n}\nprint(res)\n</pre>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-4-5\" class=\"outline-3\">\n<h3 id=\"sec-4-5\"><span class=\"section-number-3\">4.5</span> Directory Traversion</h3>\n<div class=\"outline-text-3\" id=\"text-4-5\">\n<p>\nImagine you want to traverse a file hierachy and find:\n</p>\n<ul class=\"org-ul\">\n<li>all \"psd\" files from customer1 and customer2 \n</li>\n<li>all \"blend\" files from customer2\n</li>\n<li>all \"jpeg\" files from all customers.\n</li>\n</ul>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">guard let enumerator = NSFileManager.defaultManager().enumeratorAtPath(\"/customers/2014/\")\nelse { return }\n\nfor url in enumerator {\n switch (url.pathComponents, url.pathExtension) {\n\n // psd files from customer1, customer2\n case (let f, \"psd\") \n\t where f.contains(\"customer1\") \n\t || f.contains(\"customer2\"): print(url)\n\n // blend files from customer2\n case (let f, \"blend\") where f.contains(\"customer2\"): print(url)\n\n // all jpg files\n case (_, \"jpg\"): print(url)\n\n default: ()\n }\n}\n</pre>\n</div>\n\n<p>\nNote that <code>contains</code> stops at the first match and doesn't traverse the complete path.\nAgain, pattern matching lead to very succinct and readable code.\n</p>\n</div>\n</div>\n\n<div id=\"outline-container-sec-4-6\" class=\"outline-3\">\n<h3 id=\"sec-4-6\"><span class=\"section-number-3\">4.6</span> Fibonacci</h3>\n<div class=\"outline-text-3\" id=\"text-4-6\">\n<p>\nAlso, see how beautiful an implementation of the fibonacci algorithm looks with pattern matching <sup><a id=\"fnr.3\" name=\"fnr.3\" class=\"footref\" href=\"#fn.3\">3</a></sup>\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">func fibonacci(i: Int) -> Int {\n switch(i) {\n case let n where n <= 0: return 0\n case 0, 1: return 1\n case let n: return fibonacci(n - 1) + fibonacci(n - 2)\n }\n}\n\nprint(fibonacci(8))\n</pre>\n</div>\n\n<p>\nOf course, this will kill your stack with big numbers.\n</p>\n</div>\n</div>\n\n<div id=\"outline-container-sec-4-7\" class=\"outline-3\">\n<h3 id=\"sec-4-7\"><span class=\"section-number-3\">4.7</span> Legacy API and Value Extractions</h3>\n<div class=\"outline-text-3\" id=\"text-4-7\">\n<p>\nOftentimes, when you get data from an external source, like a library, or an API, it is not only good practice but usually even required that you check the data for consistency before interpreting it. You need to make sure that all keys exists or that the data is of the correct type, or the arrays have the required length. Not doing so can lead from buggy behaviour (missing key) to crash of the app (indexing non-existent array items). The classic way to do this is by nesting <code>if</code> statements. \n</p>\n\n<p>\nLet's imagine an API that returns a user. However, there're two types of users: System users - like the administrator, or the postmaster - and local users - like \"John B\", \"Bill Gates\", etc. Due to the way the system was designed and grew, there're a couple of nuisances that API consumers have to deal with:\n</p>\n<ul class=\"org-ul\">\n<li><code>system</code> and <code>local</code> users come via the same API call.\n</li>\n<li>the <code>department</code> key may not exist, since early versions of the db did not have that field and early employees never had to fill it out.\n</li>\n<li>the <code>name</code> array contains either 4 items (username, middlename, lastname, firstname) or 2 items (full name, username) depending on when the user was created.\n</li>\n<li>the <code>age</code> is an Integer with the age of the user\n</li>\n</ul>\n\n<p>\nOur system needs to create user accounts for all system users from this API with only the following information: username, department. We only need users born before 1980. If no department is given, \"Corp\" is assumed.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">func legacyAPI(id: Int) -> [String: AnyObject] {\n return [\"type\": \"system\", \"department\": \"Dark Arts\", \"age\": 57, \n\t \"name\": [\"voldemort\", \"Tom\", \"Marvolo\", \"Riddle\"]] \n}\n</pre>\n</div>\n\n<p>\nGiven these constraints, let's develop a pattern match for it:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let item = legacyAPI(4)\nswitch (item[\"type\"], item[\"department\"], item[\"age\"], item[\"name\"]) {\n case let (sys as String, dep as String, age as Int, name as [String]) where \n age < 1980 &&\n sys == \"system\":\n createSystemUser(name.count == 2 ? name.last! : name.first!, dep: dep ?? \"Corp\")\n default:()\n}\n\n// returns (\"voldemort\", \"Dark Arts\")\n</pre>\n</div>\n\n<p>\nNote that this code makes one dangerous assumption, which is that if the name array does not have 2 items, it <b>must</b> have 4 items. If that case doesn't hold, and we get a zero item name array, this would crash. \n</p>\n\n<p>\nOther than that, it is a nice example of how pattern matching even with just one case can help you write cleaner code and simplify value extractions.\n</p>\n\n<p>\nAlso, see how we're writing <code>let</code> at the beginning right after the case, and don't have to repeat it for each assignment within the case.\n</p>\n</div>\n</div>\n</div>\n\n\n\n<div id=\"outline-container-sec-5\" class=\"outline-2\">\n<h2 id=\"sec-5\"><span class=\"section-number-2\">5</span> Patterns with other Keywords</h2>\n<div class=\"outline-text-2\" id=\"text-5\">\n<p>\nThe Swift documentation points out, that not all patterns can be used with the <code>if</code>, <code>for</code> or the <code>guard</code> statement. However, the docs seem to be outdated. All 7 patterns work for all three keywords.\n</p>\n\n<p>\nFor those interested, I compiled an example Gist that has an example for each pattern for each keyword.\n</p>\n\n<p>\n<a href=\"https://gist.github.com/terhechte/6eaeb90276bbfcd1ea41\">You can see the example patterns here.</a>\n</p>\n\n<p>\nAs a shorter example, see the <b>Value Binding</b>, <b>Tuple</b>, and <b>Type Casting</b> pattern used for all three keywords in one example:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">// This is just a collection of keywords that compiles. This code makes no sense\nfunc valueTupleType(a: (Int, Any)) -> Bool {\n // guard case Example\n guard case let (x, _ as String) = a else { return false}\n print(x)\n\n // for case example\n for case let (a, _ as String) in [a] {\n\tprint(a)\n }\n\n // if case example\n if case let (x, _ as String) = a {\n print(\"if\", x)\n }\n\n // switch case example\n switch a {\n case let (a, _ as String):\n\tprint(a)\n\treturn true\n default: return false\n }\n}\nlet u: Any = \"a\"\nlet b: Any = 5\nprint(valueTupleType((5, u)))\nprint(valueTupleType((5, b)))\n// 5, 5, \"if 5\", 5, true, false\n</pre>\n</div>\n\n<p>\nWith this in mind, we will have a short look at each of those keywords in detail.\n</p>\n</div>\n</div>\n\n<div id=\"outline-container-sec-6\" class=\"outline-2\">\n<h2 id=\"sec-6\"><span class=\"section-number-2\">6</span> Using <b>for case</b></h2>\n<div class=\"outline-text-2\" id=\"text-6\">\n<p>\nWith Swift 2.0, pattern matching has become even more important in the language as the <code>switch</code> capabilities have been extended to other keywords as well. For example, let's write a simple array function which only returns the non-nil elements\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">func nonnil<T>(array: [T?]) -> [T] {\n var result: [T] = []\n for case let x? in array {\n result.append(x)\n }\n return result\n}\n\nprint(nonnil([\"a\", nil, \"b\", \"c\", nil]))\n</pre>\n</div>\n\n<p>\nThe <code>case</code> keyword can be used in for loops just like in <code>switch</code> cases. Here's another example. Remember the game we talked about earlier? Well, after the first refactoring, our entity system now looks like this:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">enum Entity {\n enum EntityType {\n\tcase Soldier\n\tcase Player\n }\n case Entry(type: EntityType, x: Int, y: Int, hp: Int)\n}\n</pre>\n</div>\n\n<p>\nFancy, this allows us to draw all items with even less code:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">for case let Entity.Entry(t, x, y, _) in gameEntities()\nwhere x > 0 && y > 0 {\n drawEntity(t, x, y)\n}\n</pre>\n</div>\n\n<p>\nOur one line unwraps all the necessary properties, makes sure we're not drawing beyond 0, and finally calls the render call (<code>drawEntity</code>).\n</p>\n\n<p>\nIn order to see if the player won the game, we want to know if there is at least one Soldier with health > 0\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">func gameOver() -> Bool {\n for case Entity.Entry(.Soldier, _, _, let hp) in gameEntities() \n where hp > 0 {return false}\n return true\n}\nprint(gameOver())\n</pre>\n</div>\n\n<p>\nWhat's nice is that the <code>Soldier</code> match is part of the for query. This feels a bit like <code>SQL</code> and less like imperative loop programming. Also, this makes our intent clearer to the compiler, opening up the possibilities for dispatch enhancements down the road. Another nice touch is that we don't have to spell out <code>Entity.EntityType.Soldier</code>. Swift understands our intent even if we only write <code>.Soldier</code> as above.\n</p>\n</div>\n</div>\n\n<div id=\"outline-container-sec-7\" class=\"outline-2\">\n<h2 id=\"sec-7\"><span class=\"section-number-2\">7</span> Using <b>guard case</b></h2>\n<div class=\"outline-text-2\" id=\"text-7\">\n<p>\nAnother keyword which supports patterns is the newly introduced <code>guard</code> keyword. You know how it allows you to bind <code>optionals</code> into the local scope much like <code>if let</code> only without nesting things:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">func example(a: String?) {\n guard let a = a else { return }\n print(a)\n}\nexample(\"yes\")\n</pre>\n</div>\n\n<p>\n<code>guard let case</code> allows you to do something similar with the power that pattern matching introduces. Let's have a look at our soldiers again. We want to calculate the required HP until our player has full health again. Soldiers can't regain HP, so we should always return 0 for a soldier entity.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">let MAX_HP = 100\n\nfunc healthHP(entity: Entity) -> Int {\n guard case let Entity.Entry(.Player, _, _, hp) = entity \n where hp < MAX_HP \n else { return 0 }\n return MAX_HP - hp\n}\n\nprint(\"Soldier\", healthHP(Entity.Entry(type: .Soldier, x: 10, y: 10, hp: 79)))\nprint(\"Player\", healthHP(Entity.Entry(type: .Player, x: 10, y: 10, hp: 57)))\n\n// Prints:\n\"Soldier 0\"\n\"Player 43\"\n</pre>\n</div>\n\n<p>\nThis is a beautiful example of the culmination of the various mechanisms we've discussed so far. \n</p>\n\n<ul class=\"org-ul\">\n<li>It is very clear, there is no nesting involved\n</li>\n<li>Logic and initialization of state are handled at the top of the <code>func</code> which improves readability\n</li>\n<li>Very terse.\n</li>\n</ul>\n\n<p>\nThis can also be very successfully combined with <code>switch</code> and <code>for</code> to wrap complex logical constructs into an easy to read format. Of course, that won't make the logic any easier to understand, but at least it will be provided in a much saner package. Especially if you use <code>enums</code>.\n</p>\n</div>\n</div>\n\n<div id=\"outline-container-sec-8\" class=\"outline-2\">\n<h2 id=\"sec-8\"><span class=\"section-number-2\">8</span> Using <b>if case</b></h2>\n<div class=\"outline-text-2\" id=\"text-8\">\n<p>\n<code>if case</code> can be used as the opposite of <code>guard case</code>. It is a great way to unwrap and match data within a branch. In line with our previous <code>guard</code> example. Obviously, we need an move function. Something that allows us to say that an entity moved in a direction. Since our entities are <code>enums</code>, we need to return an updated entity.\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\" id=\"feature-image\">func move(entity: Entity, xd: Int, yd: Int) -> Entity {\n\tif case Entity.Entry(let t, let x, let y, let hp) = entity\n\twhere (x + xd) < 1000 &&\n\t (y + yd) < 1000 {\n\treturn Entity.Entry(type: t, x: (x + xd), y: (y + yd), hp: hp)\n }\n return entity\n}\nprint(move(Entity.Entry(type: .Soldier, x: 10, y: 10, hp: 79), xd: 30, yd: 500))\n// prints: Entry(main.Entity.EntityType.Soldier, 40, 510, 79)\n</pre>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-9\" class=\"outline-2\">\n<h2 id=\"sec-9\"><span class=\"section-number-2\">9</span> Limitations</h2>\n<div class=\"outline-text-2\" id=\"text-9\">\n<p>\nSome limitations were already mentioned in the text, such as the issues regarding <code>Expression Patterns</code>, which seem to not match against <code>tuples</code> (as would be really convenient). In Scala or Clojure, pattern matching can also work against collections, so you could match head, tail, parts, etc. <sup><a id=\"fnr.4\" name=\"fnr.4\" class=\"footref\" href=\"#fn.4\">4</a></sup> This doesn't work in Swift (<a href=\"http://austinzheng.com/2014/12/17/custom-pattern-matching/\">although Austin Zheng kinda implemented this in the blog post I linked above</a>).\n</p>\n\n<p>\nAnother thing which doesn't work (wich, again, Scala does just fine) is destructuring against classes or structs. Scala allows us to define an <code>unapply</code> method which does basically the opposite of <code>init</code>. Implementing this method, then, allows the type checker to match against classes. In Swift, this could look as follows:\n</p>\n\n<div class=\"org-src-container\">\n\n<pre class=\"src src-swift\">struct Imaginary {\n let x: Int\n let y: Int\n func unapply() -> (Int, Int) {\n // implementing this method would then in theory provide all the details needed to destructure the vars\n return (self.x, self.y)\n }\n}\n// this, then, would unapply automatically and then match\nguard case let Imaginary(x, y) = anImaginaryObject else { break }\n</pre>\n</div>\n</div>\n</div>\n\n<div id=\"outline-container-sec-10\" class=\"outline-2\">\n<h2 id=\"sec-10\"><span class=\"section-number-2\">10</span> Changes</h2>\n<div class=\"outline-text-2\" id=\"text-10\">\n<p>\n<b><b>08/21/2015</b></b> Incorporated <a href=\"https://www.reddit.com/r/swift/comments/3hq6id/match_me_if_you_can_swift_pattern_matching_in/\">helpful feedback from foBrowsing on Reddit</a>\n</p>\n<ul class=\"org-ul\">\n<li>Added <code>guard case let</code>\n</li>\n<li>Added simplified syntax for let (i.e. <code>let (x, y)</code> instead of <code>(let x, let y)</code>\n</li>\n</ul>\n<p>\n<b><b>08/22/2015</b></b> <a href=\"https://www.reddit.com/r/swift/comments/3hq6id/match_me_if_you_can_swift_pattern_matching_in/\">Apparently I didn't test some things properly enough.</a> Some of the limitations I listed do actually work, as another helpful Reddit commenter (latrodectus) pointed out.\n</p>\n<ul class=\"org-ul\">\n<li>All patterns work for all three keywords. Changed that, and added a Gist with examples\n</li>\n<li>The limitations regarding protocols and the expression pattern were invalid. This works fine, too.\n</li>\n<li>Added \"Pattern Availability\" section\n</li>\n</ul>\n<p>\n<b><b>08/24/2015</b></b> \n</p>\n<ul class=\"org-ul\">\n<li>Added <code>if case</code> examples, renamed some sections.\n</li>\n<li>Fixed typos in the text. In particular, I accidentally wrote that <code>_</code> does not match <code>nil</code>. That's of course not true, <code>_</code> matches everything. (thanks to <a href=\"https://github.com/obecker\">obecker</a>)\n</li>\n</ul>\n<p>\n<b><b>09/18/2015</b></b>\n</p>\n<ul class=\"org-ul\">\n<li>Added link to Japanese Translation\n</li>\n</ul>\n</div>\n</div>\n<div id=\"footnotes\">\n<h2 class=\"footnotes\">Footnotes: </h2>\n<div id=\"text-footnotes\">\n\n<div class=\"footdef\"><sup><a id=\"fn.1\" name=\"fn.1\" class=\"footnum\" href=\"#fnr.1\">1</a></sup> <p>Think of it like the <code>*</code> wildcard you use in the shell</p></div>\n\n<div class=\"footdef\"><sup><a id=\"fn.2\" name=\"fn.2\" class=\"footnum\" href=\"#fnr.2\">2</a></sup> <p>I'm not sure whether the compiler optimizes for this, but theoretically, it should be able to calculate the correct position of the requested data and inline the address ignoring the other parts of the enum case</p></div>\n\n<div class=\"footdef\"><sup><a id=\"fn.3\" name=\"fn.3\" class=\"footnum\" href=\"#fnr.3\">3</a></sup> <p>of course, no match for a Haskell implementation: <br />\nfib 0 = 0<br />\nfib 1 = 1<br />\nfib n = fib (n-1) + fib (n-2)</p></div>\n\n<div class=\"footdef\"><sup><a id=\"fn.4\" name=\"fn.4\" class=\"footnum\" href=\"#fnr.4\">4</a></sup> <p>I.e. switch [1, 2, 4, 3] { <br />\ncase [_, 2, _, 3]: <br />\n}</p></div>\n\n\n</div>\n</div>",
:keywords
"feature lisp swift optional scala simple optionals switch chaining for pattern matching clojure haskell",
:title "Match Me if you can: Swift Pattern Matching in Detail.",
:filename "2015-08-20-swift-pattern-matching-in-detail.org",
:id 655205247,
:url "/2015/08/20/swift-pattern-matching-in-detail/",
:javadate #inst "2015-08-19T22:00:00.000-00:00",
:keyword-keywords
(:feature
:lisp
:swift
:optional
:scala
:simple
:optionals
:switch
:chaining
:for
:pattern
:matching
:clojure
:haskell)}]