Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

super init constructor in Swift

I used to work with Objective-c using the following code in my class NSObject constructor :

- (id)init {
    self = [super init] ;
    return self;
}

How do I use it in Swift?

I tried to do this:

override init() {
    self = super.init()
    return self;
}

I'm getting two errors:

cannot assign value self is immutable
nil is the only return value permitted in this initializer  
like image 294
Nata Mio Avatar asked Nov 09 '15 08:11

Nata Mio


People also ask

What does super init do in Swift?

The init() initializer for Bicycle starts by calling super. init(), which calls the default initializer for the Bicycle class's superclass, Vehicle. This ensures that the numberOfWheels inherited property is initialized by Vehicle before Bicycle has the opportunity to modify the property. After calling super.

What is Failable initializer in Swift?

In a failable initializer, return nil indicates that initialization has failed; no other value can be returned. In the example, failure occurs when the string could not be parsed as an integer. Otherwise, self is initialized to the parsed value.


3 Answers

You can't assign to self in Swift. Just use

super.init()

You also don't return anything. Constructors are of type void (in C lingo).

like image 183
Avi Avatar answered Oct 20 '22 07:10

Avi


The Swift initialization sequence has a little bit difference from Objective-C,

class BaseClass {
    var value : String
    init () {
        value = "hello"
    }
} 

the subclass below.

class SubClass : BaseClass {
    var subVar : String
    let subInt : Int

    override init() {
        subVar = "world"
        subInt = 2015
        super.init()
        value = "hello world 2015" // optional, change the value of superclass
    }

}

The initialization sequence is:

  1. Initialize subclass's var or let,
  2. Call super.init(), if the class has a super class,
  3. Change value of superclass, if you wanna do that.

I think your code:

override init() {
    self = super.init()  //just call super.init(), do not assign it to self
    return self;         //it is unnecessary to return self
}

We must remember initialize all of the var or let in the class.

like image 23
edisongz Avatar answered Oct 20 '22 07:10

edisongz


In Swift, you don't assign or return self. In addition, you need to call super.init() after custom initialization. I.e., if your Objective-C code looked something like:

- (instancetype)init {
    if (self = [super init]) {
        someProperty = 42;
    }
}

then the equivalent in Swift would be

init() {
    self.someProperty = 42
    super.init()
}

The reason for this is stated in the Apple documentation:

Safety check 1 A designated initializer must ensure that all of the properties introduced by its class are initialized before it delegates up to a superclass initializer.

As mentioned above, the memory for an object is only considered fully initialized once the initial state of all of its stored properties is known. In order for this rule to be satisfied, a designated initializer must make sure that all of its own properties are initialized before it hands off up the chain.

like image 2
The Paramagnetic Croissant Avatar answered Oct 20 '22 06:10

The Paramagnetic Croissant