Will Howe
Will Howe

Reputation: 139

How to add optional values to an array in Swift

I'm having issues with appending an optional value to an array in Swift. The view I'm writing is for the creation of a routine for the gym. However my Routine object is not being instantiated as it should be.

I have experience with other programming languages but I am fairly new to Swift, and optionals.

My ViewController contains an optional variable:

var routine: Routine?

Where the Routine class contains:

name: String
exerciseList: [String]()
numOfSets: [Int]()

When I am preparing it to send the newly created routine to my other ViewController, I take the values from user input to edit the fields of the object.

let name = routineName.text ?? ""
let numberOne = Int(numOfSetsOne.text ?? "0") //numOfSetsOne is a text label
routine?.exerciseList.append(selectedExerciseOne!) //Haven't tested to see if this works yet
routine?.numOfSets[0] = numberOne! //This line is not working 
routine = Routine(name: name)

To try a little debugging I put print statements on either side of the line like so:

print ("numberOne Value: \(numberOne!)")
routine?.numOfSets[0] = numberOne!
print ("numOfSets[0] Value: \(routine?.numOfSets[0])")

I expected the output from the second print statement to be identical to the first. However the terminal output:

numberOne Value: 3
numOfSets[0] Value: nil

Does anyone know what has gone wrong here? Thanks

Upvotes: 2

Views: 766

Answers (2)

Paulw11
Paulw11

Reputation: 114975

You have declared a property that may contain a Routine, but you have not assigned an instance of Routine to that property before trying to use it.

This means that, for example,

routine?.numSets[0] = numberOne! 

doesn't do anything - routine is nil and so the statement is skipped.

You should create an appropriate init function for your Routine class and use that to create a new Routine and assign it to routine

For example:

class Routine {
    var name: String
    var exerciseList = [String]()
    var numberOfSets = [Int]()

    init(named: String) {
        self.name = named
    }
}

Then you can say

let name = routineName.text ?? ""
let numberOne = Int(numOfSetsOne.text ?? "0") 
self.routine = Routine(named: name)
self.routine?.numberOfSets.append(numberOne!)

Coordinating related arrays can get a bit messy, so I would use a single array:

struct ExerciseSet {
    let exerciseName: String
    let sets: Int
}


class Routine {
    var name: String
    var exerciseList = [ExerciseSet]()

    init(named: String) {
        self.name = named
    }
}

Upvotes: 3

Razi Tiwana
Razi Tiwana

Reputation: 1435

Your Routine is not initialised before its being assigned value

try

let name = routineName.text ?? ""
let numberOne = Int(numOfSetsOne.text ?? "0") 

routine = Routine(name: name)

routine?.exerciseList.append(selectedExerciseOne!) 
routine?.numOfSets[0] = numberOne!  

Upvotes: 1

Related Questions