swift

Extensions allow you to add functionality to existing classes, structures, enumerations, and protocols.

Through an example, everything will be clear: we are going to create extended features to the Double type (which is a structure), for this we declare the constant distance as a Double and then we add conversion properties between Km, m, cm, and so on..

extension Double {

    var Km: Double { return self / 1000.0 }

    var m: Double { return self }

    var cm: Double { return self * 100.0 }

    var mm: Double { return self * 1000.0 }

}

let distance: Double = 200.m

print(distance.Km) //It prints: 0.2

 

With extension, we have created a Double type extension by adding computed properties which are no more than variables that can return a calculated value to the value assumed by the same variable (use of the self keyword).

The Km extension is declared by the usual syntax for the variables and is defined as Double; its value however is the result of the calculation obtained from the value of the variable itself (self statement) divided by 1000.

In the example, distance value is 200 meters. Next reading the property distance.Km we get the recomputed value (200m = 0.2Km).

Extensions can be used to create methods to add behaviors or modify existing ones.

Suppose you want to modify the Int type so that you add a property that repeats an arbitrary number of times a function. It is definitely a bizarre behavior but highlights the power of extension. What we want to get is that 3.repeat {print ("Hello")} prints three times the string "Hello".

extension Int {

    func repeat(task: () -> Void) {

        for _ in 0..<self {

            task()

        }

    }

}

3.repeat {

    print("Hello")

}

//Hello

//Hello

//Hello

 

An extension is created to the Int type and the repeat function is defined. This function takes as a parameter the type () -> Void which means a function without any parameter that does not return anything. In Swift almost everything is a type, so in addition to the types traditionally known in programming as int or char there are types like the one described above that identify a certain type of function: one that does not take parameters and does not return values. 

The repeat function performs a for loop with the counter going from 0 to the value indicated by the integer (self = 3 in the example), the for loop repeats for self times the function passed in the task parameter. The underscore character in the for loop is used to avoid to define a variable that is not being used.

The extension can also change the value initially attributed to the variable. Let's make an example of an Int variable that is redefined by a function created within the extension.

extension Int {

    mutating func cubed() {

        self = self * self * self

    }

}

var myInt = 3

myInt.cubed()

print(myInt)

// It prints 27

 

If the function defined in the extension modifies or changes the value initially attributed to the variable, the function must be defined as mutating.