Coding – Let the Swift Compiler Help You

One of the bigger differences for me as I was learning Swift and starting to code with this new language was getting into a new flow where I style my code a bit differently to let the compiler help me accomplish my goals and enforce complete code.

An Example, with bugs

So, here’s a little example of a situation I’ve run thru a number of different ways, complete with some bugs! 🙂

Figure 1 – The first code, with bugs!

In Figure 1, we have an updateLight() function. This function is responsible for setting a stoplight to be either red (stop), yellow (caution/slow), green (go), blinking red (stop, then proceed), or blinking yellow (yield, proceed with caution). (Note: these are my descriptions and not any official definitions for what the lights mean, so please consult your local rules of the road and not my blog).

This has a few bugs you might have spotted already. For one thing, we can never set the light to blinking red. For another, once we start blinking, we never stop!

So, let’s fix a few of these problems…

Figure 2 – LET us make a plan

In Figure 2, I’ve arranged around this logic a pattern I use often in Swift. Before the “logic stuff” we make constants (with let) but do not assign them any value. After the “logic stuff” we use those constants.

And, right away, the compiler has build errors because there are some times where we did not set color or isBlinking. Perfect, the compiler is now helping me see that I have bugs! I just have to fix up the problem. Oh I see, I didn’t set isBlinking to false in these other if statements. That’s why the stoplight would keep blinking!

Ok, I’ve cleaned that up by adding isBlinking = false everywhere.

Figure 3 – closer, but no build

We set color and isBlinking in all of these cases, so we’re done. But wait, the compiler is still giving me build errors?! This is wonderful! The compiler found a bug for me that I couldn’t see. So what is it? If all of my if statements are false, then nothing sets color or isBlinking, so I’ll add an else at the end of all of this. But what should I do if the light doesn’t really have a setting for go or warning or stop? I don’t know what to do.

If this were on a project, I’d start asking questions.

If this were on a project, I’d start asking questions. Will we ever have stoplights with different colors? What is the standard behavior for a newly installed stoplight? And just like that, the Swift compiler has helped me find something I didn’t think about and gave me the right questions to ask.

For this example, I’m going to say that a light we don’t know what to do with should be a blinking red light.

Figure 4 – It builds! We’re done, right?

This one builds! So if I’m not sure what to do with the light, I’ll just set it to blinking red. Then it acts like a stop sign and that feels like the safest choice.

This code looks too complicated and it’s giving these weird extra cases. I think I can do better.

Switch to the rescue

Whenever I have a few if statements inside each other, there’s often a better way to handle that with a switch. So let’s use a switch to clean it up a bit.

Figure 5 – Switch instead of ifs

This feels a little better, because now I’ve got the go, warning, stop handled. I can make sure we don’t do blinking green, and it’s a bit clearer that we are handling the weird case of “none of the above” by setting to blinking red instead.

I get compiler errors for every switch so I know exactly where I need to go update my code

Switch statements are available in almost every coding language, but in Swift, the complier enforces that you provide a case for every possibility. This is the most useful when you use types that only have so many values. I use Switch with my own enums all the time, and then when I add a new case, I get compiler errors for every switch so I know exactly where I need to go update my code and think about how to handle that new case.

In fact, I’d like to make an enum to make the different “modes” or styles of the stoplight into a simple list of options. Let’s make a “style” attribute on the light and then my switch statement becomes a switch on one only the style. I also didn’t define anything that means “blinking green” and I don’t have to handle the “I don’t know what to do” case because the enum has exactly (and only) the 5 possibilities for the light. When I make a new light, I’ll set the style to .stopBlinking and I’m all set.

Figure 6 – An enum to the rescue

Ok, we finally finished, right?

Well… this is certainly much better than what we started with. We handle all the cases. We’ve factored out the bugs we had before, and we’ve made the enum type to handle the specific list of cases we cared about.

But, our code got longer, and maybe I need to use color or blinking information about a light somewhere else.

Figure 7 – 2-line function and some extensions!

Figure 7 has the approach we end up with. This uses extensions to add the color and blinking generated variables to the Light, and now we can use those from elsewhere in our code. Each extension does a switch, so if we do add a new style for our stoplights (blinking green?, different colors, arrows?), the Swift compiler will help us see what we need to think about and change.

If you use a switch with an enum, but not providing a default, if you change the enum, then the compiler will show build errors thru your code so you can see exactly what you need to change.

always do your future self a favor

Some extra benefits of this being an extension on the Light is that color and blinking can now be found by future developers (always do your future self a favor — even if you aren’t sharing your code), because they are variables on the Light itself. Just take myLight. (press esc) and see the blinking and color come up as options.

Summary

We’ve used unassigned lets before code to make sure we assign the value we want in some if logic. We used a switch statement to flatten out the if statements. We used a custom enum to make our short list of possibilities. We used extensions to split up some overlapping ideas, make the code available elsewhere, and keep it close to the actual type so it can be discovered more easily.

When you use the Swift compiler to your advantage, it can guide your code to find and handle all the possibilities of what can happen.

Cleaning your devices

In light of the COVID-19 pandemic, thinking about surfaces you touch often and how to keep them clean is on my mind. Apple recently updated their cleaning guidelines. The short story is, you can use certain disinfecting wipes on your devices. But you should use them rarely.

I’ll suggest these steps to improve your habits around using devices. Like a lot of the public health information going around, these are good habits to be using all the time:

  • Wash hands before using technology — tv remotes, game controllers, iPads, etc.
  • Clean devices regularly with a cloth
  • Don’t mix food and touchscreens

Star Wars: Galaxy’s Edge

This place is amazing to me. I am not at a park when I’m here. I’m in Star Wars.

My iPhone transformed into a Datapad. I hacked into a landspeeder and heard it’s engines rev up. I hacked an X-Wing and heard it bleep and bloop and sputter, while the lights flash. I hacked an A-Wing and it revved so loud it drew a crowd. I hacked the Millennium Falcon and made bursts of air come down underneath it.

I am so impressed with all the little details of this land. I could spend an hour in each space, taking in the nods to moments of films and shows and more.

A rebel with blue-tipped hair walked past me, coolly nodding, headed straight for trouble on the First Order side of the Spire. I wanted to follow and see where her story goes next.

til the spire

Updated Maps on Apple Devices

Apple updated their maps across the United States today. You’ll be able to see more details with outlines of buildings on the Map view, and some more terrain applied in 3D.

I was impressed to see a lot of detail carved out in my own house, and I’m excited to try out directions to see if how pedestrian directions have been improved.

My kids love looking at maps and I’m excited to see what new details they find after this update.

Magic Kingdom Park with 3D building outlines

DoubleTake app

This app is a great free app for using two of your iPhone cameras at the same time.

First: this only works with some of the newest iPhones: Xs, Xr, 11, 11 Pro — and the Max varieties.

I’ve played around with it a bit and am excited about using this for:

  • Quick demo videos to capture a selfie camera at the same time as what’s in front of me at the same time
  • Wide and detail views using different cameras

This app is free. The catch is, it includes a button linking to Filmic’s pro camera app (currently $15) with more full-featured multi-camera functionality.

https://apps.apple.com/us/app/doubletake-by-filmic-pro/id1478041592

One thing to be safer online

Use a different password for every account.

If you are using the same password, or obvious variations of the same password, on each site you login to, then your password is only as safe as the site that gets hacked next.

If you use only Apple devices, then iCloud Keychain does a great job of suggesting good passwords and storing them securely for you.

Once you are ready for a little more — like sharing some passwords between members of your family automatically, I recommend a good password manager, like 1Password or LastPass. These tools will help you manage changing your passwords regularly, inform you when a password is leaked, and more.