Updated for Xcode 14.2
Class initializers in Swift are more complicated than struct initializers, but with a little cherrypicking we can focus on the part that really matters: if a child class has any custom initializers, it must always call the parent’s initializer after it has finished setting up its own properties, if it has any.
Like I said previously, Swift won’t automatically generate a memberwise initializer for classes. This applies with or without inheritance happening – it will never generate a memberwise initializer for you. So, you either need to write your own initializer, or provide default values for all the properties of the class.
Let’s start by defining a new class:
class Vehicle {
let isElectric: Bool
init(isElectric: Bool) {
self.isElectric = isElectric
}
}
That has a single Boolean property, plus an initializer to set the value for that property. Remember, using self
here makes it clear we’re assigning the isElectric
parameter to the property of the same name.
Now, let’s say we wanted to make a Car
class inheriting from Vehicle
– you might start out writing something like this:
class Car: Vehicle {
let isConvertible: Bool
init(isConvertible: Bool) {
self.isConvertible = isConvertible
}
}
But Swift will refuse to build that code: we’ve said that the Vehicle
class needs to know whether it’s electric or not, but we haven’t provided a value for that.
What Swift wants us to do is provide Car
with an initializer that includes both isElectric
and isConvertible
, but rather than trying to store isElectric
ourselves we instead need to pass it on – we need to ask the super class to run its own initializer.
Here’s how that looks:
class Car: Vehicle {
let isConvertible: Bool
init(isElectric: Bool, isConvertible: Bool) {
self.isConvertible = isConvertible
super.init(isElectric: isElectric)
}
}
super
is another one of those values that Swift automatically provides for us, similar to self
: it allows us to call up to methods that belong to our parent class, such as its initializer. You can use it with other methods if you want; it’s not limited to initializers.
Now that we have a valid initializer in both our classes, we can make an instance of Car
like so:
let teslaX = Car(isElectric: true, isConvertible: false)
Tip: If a subclass does not have any of its own initializers, it automatically inherits the initializers of its parent class.
SPONSORED Thorough mobile testing hasn’t been efficient testing. With Waldo Sessions, it can be! Test early, test often, test directly in your browser and share the replay with your team.
Sponsor Hacking with Swift and reach the world's largest Swift community!
Link copied to your pasteboard.