Reader small image

You're reading from  Object???Oriented Programming with Swift 2

Product typeBook
Published inJan 2016
Reading LevelIntermediate
Publisher
ISBN-139781785885693
Edition1st Edition
Languages
Tools
Right arrow
Author (1)
Gaston C. Hillar
Gaston C. Hillar
author image
Gaston C. Hillar

Gaston C. Hillar is Italian and has been working with computers since he was 8 years old. Gaston has a Bachelor's degree in computer science (graduated with honors) and an MBA. Currently, Gaston is an independent IT consultant and a freelance author who is always looking for new adventures anywhere in the world. He was a senior contributing editor at Dr. Dobb's, and has written more than a hundred articles on software development topics. He has received the prestigious Intel Black Belt Software Developer award eight times. He has written many articles about Java for Oracle Java Magazine. Gaston was also a former Microsoft MVP in technical computing. He lives with his wife, Vanesa, and his two sons, Kevin and Brandon.
Read more about Gaston C. Hillar

Right arrow

Chapter 2. Structures, Classes, and Instances

In this chapter, you will learn the differences between structures and classes. We will start working with examples on how to code classes and customize the initialization and deinitialization of instances. We will understand how classes work as blueprints to generate instances and dive deep on all the details of automatic reference counting, also known as ARC.

Understanding structures, classes, and instances


In the previous chapter, you learned some of the basics of the object-oriented paradigm, including classes and objects, which are also known as instances. We started working on an app required by an acrylic paint manufacturer that wanted to take full advantage of the popularity of a popular YouTuber, painter, and craftswoman. We ended up creating a UML diagram with the structure of many classes, including their hierarchy, properties, and methods. It is time to take advantage of the Playground to start coding the classes and work with them.

In Swift, a class is always the type and blueprint. The object is the working instance of the class, and one or more variables can hold a reference to an instance. An object is an instance of the class, and the variables can be of a specific type (that is, a class) and hold objects of the specific blueprint that we generated when declaring the class.

It is very important to mention some of the differences...

Understanding initialization and its customization


When you ask Swift to create an instance of a specific class, something happens under the hood. Swift creates a new instance of the specified type, allocates the necessary memory, and then executes the code specified in the initializer.

Tip

You can think of initializers as equivalents of constructors in other programming languages such as C# and Java.

When Swift executes the code within an initializer, there is already a live instance of the class. Thus, we have access to the properties and methods defined in the class. However, we must be careful in the code we put in the initializer because we might end up generating huge delays when we create instances of the class.

Tip

Initializers are extremely useful to execute setup code and properly initialize a new instance.

So, for example, before you can call either the CalculateArea or CalculatePerimeter method, you want both the semiMajorAxis and semiMinorAxis fields for each new Ellipse instance...

Understanding deinitialization and its customization


At some specific times, our app won't require to work with an instance anymore. For example, once you calculate the perimeter of a regular hexagon and display the results to the user, you don't need the specific RegularHexagon instance anymore. Some programming languages require you to be careful about leaving live instances alive, and you have to explicitly destroy them and deallocate the memory that it consumed.

Swift uses an automatic reference counting, also known as ARC, to automatically deallocate the memory used by instances that aren't referenced anymore. When Swift detects that you aren't referencing an instance anymore, Swift executes the code specified within the instance's deinitializer before the instance is deallocated from memory. Thus, the deinitializer can still access all of the instance's resources.

Tip

You can think of deinitializers as equivalents of destructors in other programming languages such as C# and Java. You...

Understanding automatic reference counting


Automatic reference counting is very easy to understand. Imagine that we have to distribute the items that we store in a box. After we distribute all the items, we must throw the box in a recycle bin. We cannot throw the box to the recycle bin when we still have one or more items in it. Seriously, we don't want to lose the items we have to distribute because they are very expensive.

The problem has a very easy solution; we just need to count the number of items that remain in the box. When the number of items in the box reaches zero, we can get rid of the box.

Tip

One or more variables can hold a reference to a single instance of a class. Thus, it is necessary to count the number of references to an instance before Swift can get rid of an instance. When the number of references to a specific instance reaches zero, Swift can automatically and safely remove the instance from memory because nobody needs this specific instance anymore.

For example, you...

Declaring classes


The following lines declare a new minimal Circle class in Swift:

class Circle {
}

The class keyword, followed by the class name (Circle), composes the header of the class definition. In this case, the class doesn't have a parent class or superclass; therefore, there are neither superclasses listed after the class name, nor a colon (:). A pair of curly braces ({}) encloses the class body after the class header. In the forthcoming chapters, we will declare classes that inherit from another class, and therefore, they will have a superclass. In this case, the class body is empty. The Circle class is the simplest possible class we can declare in Swift.

Tip

Any new class you create that doesn't specify a superclass is considered a base class. Whenever you declare a class without a subclass, the class doesn't inherit from a universal base class, as it happens in other programming languages such as C#. Thus, the Circle class is known as a base class in Swift.

Customizing initialization


We want to initialize instances of the Circle class with the radius value. In order to do so, we can take advantage of customized initializers. Initializers aren't methods, but we will write them with syntax that is very similar to the instance methods. They will use the init keyword to differentiate from instance methods, and Swift will execute them automatically when we create an instance of a given type. Swift runs the code within the initializer before any other code within a class.

We can define an initializer that receives the radius value as an argument and use it to initialize a property with the same name. We can define as many initializers as we want to, and therefore, we can provide many different ways of initializing a class. In this case, we just need one initializer.

The following lines create a Circle class and define an initializer within the class body:

class Circle {
    var radius: Double
    init(radius: Double)
    {
        print("I'm initializing...

Customizing deinitialization


We want to know when the instances of the Circle class will be removed from memory—that is, when the objects aren't referenced by any variable and the automatic reference count mechanism decides that they have to be removed from memory. Deinitializers are special parameterless class methods that are automatically executed just before the runtime destroys an instance of a given type. Thus, we can use them to add any code we want to run before the instance is destroyed. We cannot call a deinitializer; they are only available for the runtime.

The deinitializer is a special class method that uses the deinit keyword in its declaration. The declaration must be parameterless, and it cannot return a value.

The following lines declare a deinitializer within the body of the Circle class:

deinit {
    print("I'm destroying the Circle instance with a radius value of \(radius).")
}

The following lines show the new complete code for the Circle class:

class Circle {
    var radius...

Creating the instances of classes


The following lines create an instance of the Circle class named circle within the scope of a getGeneratedCircleRadius function. The code within the function uses the created instance to access and return the value of its radius property. In this case, the code uses the let keyword to declare an immutable reference to the Circle instance named circle. An immutable reference is also known as a constant reference because we cannot replace the reference hold by the circle constant to another instance of Circle. When we use the var keyword, we declare a reference that we can change later.

After we define the new function, we will call it. Note that the screenshot displays the results of the execution of the initializer and then the deinitializer. Swift destroys the instance after the circle constant becomes out of scope because its reference count goes down from 1 to 0; therefore, there is no reason to keep the instance alive:

func getGeneratedCircleRadius() ...

Exercises


Now that you understand an instance's life cycle, it is time to spend some time in the Playground creating new classes and instances:

  • Exercise 1: Create a new Employee class with a custom initializer that requires two string arguments: firstName and lastName. Use the arguments to initialize properties with the same names as the arguments. Display a message with the values for firstName and lastName when an instance of the class is created. Display a message with the values for firstName and lastName when an instance of the class is destroyed.

    Create an instance of the Employee class and assign it to a variable. Check the messages printed in the Playground's Debug area. Assign a new instance of the Employee class to the previously defined variable. Check the messages printed in the Playground's Debug area.

  • Exercise 2: Create a function that receives two string arguments: firstName and lastName. Create an instance of the previously defined Employee class with the received arguments...

Test your knowledge


  1. Swift uses one of the following mechanisms to automatically deallocate the memory used by instances that aren't referenced anymore:

    1. Automatic Random Garbage Collector.

    2. Automatic Reference Counting.

    3. Automatic Instance Map Reduce.

  2. Swift executes an instance's deinitializer:

    1. Before the instance is deallocated from memory.

    2. After the instance is deallocated from memory.

    3. After the instance memory is allocated.

  3. A deinitializer:

    1. Can still access all of the instance's resources.

    2. Can only access the instance's methods but no properties.

    3. Cannot access any of the instance's resources.

  4. Swift allows us to define:

    1. Only one initializer per class.

    2. A main initializer and two optional secondary initializers.

    3. Many initializers with different arguments.

  5. Each time we create an instance:

    1. We must use argument labels.

    2. We can optionally use argument labels.

    3. We don't need to use argument labels.

Summary


In this chapter, you learned about an object's life cycle. You also learned how object initializers and deinitializers work. We declared our first class to generate a blueprint for objects. We customized object initializers and deinitializers and tested their personalized behavior in action with live examples in Swift's Playground. We understood how they work in combination with automatic reference counting.

Now that you have learned to start creating classes and instances, we are ready to share, protect, use and hide data with the data encapsulation features included in Swift, which is the topic of the next chapter.

lock icon
The rest of the chapter is locked
You have been reading a chapter from
Object???Oriented Programming with Swift 2
Published in: Jan 2016Publisher: ISBN-13: 9781785885693
Register for a free Packt account to unlock a world of extra content!
A free Packt account unlocks extra newsletters, articles, discounted offers, and much more. Start advancing your knowledge today.
undefined
Unlock this book and the full library FREE for 7 days
Get unlimited access to 7000+ expert-authored eBooks and videos courses covering every tech area you can think of
Renews at €14.99/month. Cancel anytime

Author (1)

author image
Gaston C. Hillar

Gaston C. Hillar is Italian and has been working with computers since he was 8 years old. Gaston has a Bachelor's degree in computer science (graduated with honors) and an MBA. Currently, Gaston is an independent IT consultant and a freelance author who is always looking for new adventures anywhere in the world. He was a senior contributing editor at Dr. Dobb's, and has written more than a hundred articles on software development topics. He has received the prestigious Intel Black Belt Software Developer award eight times. He has written many articles about Java for Oracle Java Magazine. Gaston was also a former Microsoft MVP in technical computing. He lives with his wife, Vanesa, and his two sons, Kevin and Brandon.
Read more about Gaston C. Hillar