Inheritance

A class can inherit methods, properties, and other characteristics from another class. When one class inherits from another, the inheriting class is known as a subclass , and the class it inherits from is known as its superclass . Inheritance is a fundamental behavior that differentiates classes from other types in Swift.

A simple example of inheritance:

class AClass { func doSomething () { println ( "Hello from AClass" ) } } class Subclass : AClass { } let base_object = AClass () base_object . doSomething () //> Hello from AClass let enhanced_object = Subclass () enhanced_object . doSomething () // > Hello from AClass

Overriding

You can override methods in order to provide custom behaviour. To override a method write the override keyword before the method declaration:

class AClass { func doSomething () { println ( "Hello from AClass" ) } } class Subclass : AClass { override func doSomething () { println ( "Hello from Subclass" ) } } let base_object = AClass () base_object . doSomething () //> Hello from AClass let enhanced_object = Subclass () enhanced_object . doSomething () //> Hello from Subclass

You can use the super keyword to call any method from the superclass.

... class Subclass : AClass { override func doSomething () { super . doSomething () println ( "Hello from Subclass" ) } } let enhanced_object = Subclass () enhanced_object . doSomething () //> Hello from AClass //> Hello from Subclass

Base class

A class that does not inherit from another class is called a base class , for example:

class User { var name : String ! var age : Int ! init ( name : String , age : Int ) { self . name = name self . age = age } }

The iOS and Mac OS classes ussualy inherit from NSObject, either directly on indirectly. If you have a mixt codebase I would encourage you to subclass NSObject when creating a new class:

Swift classes that are subclasses of NSObject: are Objective-C classes themselves

use objc_msgSend() for calls to (most of) their methods

for calls to (most of) their methods provide Objective-C runtime metadata for (most of) their method implementations Swift classes that are not subclasses of NSObject: are Objective-C classes, but implement only a handful of methods for NSObject compatibility

do not use objc_msgSend() for calls to their methods (by default)

for calls to their methods (by default) do not provide Objective-C runtime metadata for their method implementations (by default) Subclassing NSObject in Swift gets you Objective-C runtime flexibility but also Objective-C performance. Avoiding NSObject can improve performance if you don’t need Objective-C’s flexibility. from stackoverflow Swift native base class or NSObject

Protocols

Protocols are declared in a similar way to classes.

protocol MyFirstProtocol { // I do nothing

Protocols describe methods, properties and other requirements that are needed for a specific task. For example the UITableViewDelegate protocol lists all the methods that can be used to react to user events and configure a table view.

Note: you can mark a method as optional using the @optional keyword. All of the methods from UITableViewDelegate are optional. When you do not use the @optional keyword that method is required. The swift compiler will throw an error if a class conforms to a protocol and does not implement the required methods.

A class can conform to a protocol by placing its name after the type’s name separated by a colon, as part of their definition. Multiple protocols can be listed, and are separated by commas:

class AnotherSwiftClass : MyFirstProtocol , AnotherProtocol { ... }

If the class inherits from another one, make sure to put the superclass name before the protocol list.

class AnotherSwiftClass : AClass , MyFirstProtocol , AnotherProtocol { ... }

Note: Protocols use the same syntax as normal methods, but are not allowed to specify default values for method parameters.

One of the most overused design pattern in iOS is delegation. A class can delegate a part of it’s responsibilities to an instance of another class. This design pattern is implemented by defining a protocol that encapsulates the delegated responsibilities, such that a conforming type (known as a delegate) is guaranteed to provide the functionality that has been delegated.

Here is an example, the Player class delegates the shooting logic to the weapon:

protocol Targetable { var life : Int { get set } func takeDamage ( damage : Int ) } protocol Shootable { func shoot ( target : Targetable ) } class Pistol : Shootable { func shoot ( target : Targetable ) { target . takeDamage ( 1 ) } } class Shotgun : Shootable { func shoot ( target : Targetable ) { target . takeDamage ( 5 ) } } class Enemy : Targetable { var life : Int = 10 func takeDamage ( damage : Int ) { life -= damage println ( "enemy lost \(damage) hit points" ) if life <= 0 { println ( "enemy is dead now" ) } } } class Player { var weapon : Shootable ! init ( weapon : Shootable ) { self . weapon = weapon } func shoot ( target : Targetable ) { weapon . shoot ( target ) } } var terminator = Player ( weapon : Pistol ()) var enemy = Enemy () terminator . shoot ( enemy ) //> enemy lost 1 hit points terminator . shoot ( enemy ) //> enemy lost 1 hit points terminator . shoot ( enemy ) //> enemy lost 1 hit points terminator . shoot ( enemy ) //> enemy lost 1 hit points terminator . shoot ( enemy ) //> enemy lost 1 hit points // changing weapon because the pistol is inefficient terminator . weapon = Shotgun () terminator . shoot ( enemy ) //> enemy lost 5 hit points //> enemy is dead now

Challenges

create a Shape base class and derive from it Circle , Square and Rectangle . Shape should have two methods area() -> Float and perimeter() -> Float that both return 0. Implement the methods and add the necessary properties on Circle , Square and Rectangle .

base class and derive from it , and . should have two methods and that both return 0. Implement the methods and add the necessary properties on , and . create the same classes from the first exercise, but this time make Shape a protocol

a protocol add a resistance property to the Targetable protocol and reduce the damage taken by the enemy. Obs: you will need to change the life property type to Float in order to do this.

In case you missed it, check out Part 1 of this tutorial. And this is a complete guide to Object Oriented Programming in Swift.

If you found this useful please take a moment to share this with your friends