UPDATE: Read a more in-depth look at Swift functions in my objc.io article – The Many Faces of Swift Functions.
One of the frustrating things I’ve encountered with Swift is how to work with parameter names in functions. Sometimes the parameter name is required and sometimes it’s not. As an Objective-C developer, I LOVE having parameter names very explicitly present – I like how readable it makes the code.
Here is an example I’m talking about:
Notice how the UITableView initialization requires the frame parameter name, and the CGRect initialization requires the x, y, width, and height parameter names. But the dequeueReusableCellWithIdentifier method does NOT require the identifier parameter. In fact, if I tried to include the identifier parameter name, I would get an error prompting me to delete the parameter name:
And, of course, sometimes methods require one parameter name but not the other:
Notice that the inserRowsAtIndexPaths:withRowAnimation: method does NOT require the first parameter name (indexPaths), but does require the second one (withRowAnimation:).
So I decided to investigate a bit to make sure I got the rules down for when I write my own classes and methods. Here is what I found:
When you create a Swift class, you have to implement the init() function, where you can pass in as many parameters as you want. All the parameter names you include in the init function will require the parameter name labels when instantiating the function:
This holds true for initializing your favorite Objective-C and C objects as well:
Notice how CGRectMake and CGPointMake C functions are no longer required to instantiate a CGRect and CGPoint! Of course, you can still use these, but they’re definitely not as readable:
Just like with CGRectMake and CGPointMake, your favorite Objective-C class can still be initialized with the old initializers in some cases…
However, most of the old-style initializers are being deprecated, so I recommend using the new initializer syntax to be Swifty 🙂
If you write your own function similar to how you wrote the init function, you will end up with something like this:
Well, you may or may not be surprised and / or frustrated to find out that when you call your function, the parameter label is not required:
In fact, you’ll get an error if you try to include the name parameter label, and a pop up will prompt you to “fix it” by deleting the name label:
As an Objective-C developer, I’m pretty annoyed that requiring the parameter label is not the default. From working with the iOS APIs in Swift for the past month, this seems to be some kind of relic from the Objective-C way of naming methods…
Notice, that according to the Objective-C naming convention, the parameter name is part of the function name, so it’s repetitive to require a parameter label so that, for example, mutableArray.objectAtIndex(0) will actually be mutableArray.objectAtIndex(index: 0).
In Swift, we can separate the function name from the parameter name very smoothly. But if we do that, we need to require the parameter label. There are two ways of doing this:
Rename Your Param
You can add a different name for your param internally to the function:
As you can see, the parameter name label is now required when calling this function.
I’m not sure about you, but I can’t think of one use case where I’d want to have a different name for my parameter internally in my function than the one I use to pass in the parameter value. I also find this syntax pretty confusing to read. If you have a good use case for this, I’d love to hear about it in the comments!
Otherwise, I highly recommend following the other way of doing this:
Just add a hashtag in front of you parameter name, and it’ll be required!
Make sure to add the hashtag to every single parameter name in your function, or otherwise some parameter names will not be required!
As you can see, when I didn’t put a hashtag in front of the wiseOne parameter name, it was not required when calling the function. I personally think that’s a bad way of doing things, so hopefully Swift will change to accommodate an easier way to include parameter names by default. Meanwhile, make sure to always use hashtags in your function parameter names!
One of the cool things I’m personally excited about in Swift is the ability to set default values in your function. To set the default value, simple set the parameter equal to your default value:
To use a default value, you have to make sure that all other parameter names are required – put a hashtag in front of all of them! Oh yeah, and it’ll give you a warning about the hashtag in front of the parameter with the default value – so remove the hashtag from it… (yes, it’s that complicated!).
Now, when calling this method, you can choose to skip the parameter with the default value:
As you can see, naming your function in Swift while keeping the parameter names required can get pretty complicated. Keep in mind that this post is written as of beta 3, so there might be changes in the future (hopefully!).
Have you noticed anything cool about functions and parameter in Swift? I’d love to hear about it in the comments!