TEAM LICENSES: Save money and learn new skills through a Hacking with Swift+ team license >>

Milestone 3: Projects 4-6 -- cannot figure out how to use a struct inside ContentView

Forums > 100 Days of SwiftUI

Hi all,

I am trying to build an struct that would contain the database of answers as well as of the questions to the multiplication table challenge. I did the following inside of a playground and it works perfectly fine (or at least the way I intend it to:

import Cocoa

struct Question {
    var questions = [String]()
    var answers = [Int]()

    var questionsDatabase = [Array<String>]()
    var answersDatabase = [Array<Int>]()

    mutating func generateDatabase() {
        for i in 0...12 {
            for j in 0...i {
                questions.append("\(i) * \(j)")
                answers.append(i*j)
            }
            questionsDatabase.insert(questions, at: i)
            answersDatabase.insert(answers, at: i)
            questions.removeAll()
            answers.removeAll()
        }
    }

}

var ourTable = Question()
ourTable.generateDatabase()

print(ourTable.questionsDatabase[3]) // shows ["3 * 0", "3 * 1", "3 * 2", "3 * 3"]
print(ourTable.questionsDatabase[3][3]) // shows 3 * 3

However, if I try to get it to work inside my main project, it always crashes with a fatal error and I can see that questions, answers, questionsDatabase, answersDatabase all have 0 values - and I cannot for the life of me tell why... :(

import SwiftUI

struct MultiplicationTable {

    var questions = [String]()
    var answers = [Int]()

    var questionsDatabase = [Array<String>]()
    var answersDatabase = [Array<Int>]()

    mutating func generateDatabase() {
        for i in 0...12 {
            for j in 0...i {
                questions.append("\(i) * \(j)")
                answers.append(i*j)
            }
            questionsDatabase.insert(questions, at: i)
            answersDatabase.insert(answers, at: i)
            questions.removeAll()
            answers.removeAll()
        }
    }
}

struct ContentView: View {

    @State private var ourTable = MultiplicationTable()

    var body: some View {
        VStack {
            Image(systemName: "globe")
                .imageScale(.large)
                .foregroundStyle(.tint)
            Text(ourTable.questionsDatabase[3][3])
        }
        .onAppear {
            ourTable.generateDatabase()
        }
        .padding()
    }
}

#Preview {
    ContentView()
}

Any pointers would be highly appreciated! Thank you a ton in advance!

   

Hi, Could a solution be to add, if "not empty database" for displaying the text?

 if !ourTable.questionsDatabase.isEmpty {
           Text(ourTable.questionsDatabase[3][3])
 }

   

Hi Martin,

Thank you very much for your input. Indeed, that fixes everything :)

However, what I don't understand is why this is needed. I always assumed that everything inside of onAppear will be run first and only upon completion, the code inside of VStack gets executed. That's not the case then?

Thank you!

   

Hi,

Instead of onAppear, you can run the function with init in the structure. So the database is ready before you show the view.

init() {
        generateDatabase()
}

   

Thank you very much for your help. I think I am getting the hang of it...

1      

Hacking with Swift is sponsored by String Catalog.

SPONSORED Get accurate app localizations in minutes using AI. Choose your languages & receive translations for 40+ markets!

Localize My App

Sponsor Hacking with Swift and reach the world's largest Swift community!

Reply to this topic…

You need to create an account or log in to reply.

All interactions here are governed by our code of conduct.

 
Unknown user

You are not logged in

Log in or create account
 

Link copied to your pasteboard.