Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
657 views
in Technique[技术] by (71.8m points)

ios - 如何遍历字典,快速按下按钮加载下一项(How to iterate through a dictionary, loading the next item with button press in swift)

I am making an app that will ask a series of questions, giving a value when answering yes or no.

(我正在制作一个会问一系列问题的应用程序,在回答是或否时给出一个值。)

I have an initial view controller with a collection view of question types.

(我有一个带有问题类型集合视图的初始视图控制器。)

This view controller passes the type information to a new view controller with the question layout (image, label, buttons).

(该视图控制器将类型信息传递给具有问题布局(图像,标签,按钮)的新视图控制器。)

On the second view controller I have a switch/case statement to provide the proper dictionary results for the type that was passed in (via questionTypeReceived), populating the initial view correctly.

(在第二个视图控制器上,我有一个switch / case语句,可以为传入的类型(通过questionTypeReceived)提供正确的字典结果,从而正确地填充初始视图。)

Once you answer the question (simple yes or no) I want to update with the next question.

(回答问题后(简单的是或否),我想更新下一个问题。)

Any advice to get this done?

(有什么建议可以做到这一点吗?)

Extra info: I have the questions view controller (referred to here as secondary VC) refactored because I initially thought I wanted to reuse it, not just reload it.

(额外信息:我重构了问题视图控制器(此处称为辅助VC),因为我最初认为我想重用它,而不仅仅是重新加载它。)

All aspects work EXCEPT the reloading with the next question... Yes, that is because I don't have the code in there to do that.

(除了重新加载下一个问题外,所有方面都可以工作...是的,这是因为我那里没有代码来执行此操作。)

I have been trying different for loops in different places but keep getting errors so I go back to the current setup because there are no errors

(我在不同的地方尝试过不同的for循环,但是不断收到错误,因此我返回当前设置,因为没有错误)

Initial VC

(初始VC)

    let names = [ "Work", "School", "Family", "Friends", "Random" ]

    func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {
        questionType = names[indexPath.row] as String
        let storyboard:UIStoryboard = UIStoryboard(name: "questions", bundle: nil)
        let questionsVC = storyboard.instantiateViewController(withIdentifier: "questionsViewController") as! questionsViewController
        questionsVC.questionTypeReceived = questionType
        self.navigationController?.pushViewController(questionsVC, animated: true)
        performSegue(withIdentifier: "question_segue", sender: questionType)
    }

    override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
        guard let dest = segue.destination as? questionsViewController else {
            print("Can't perform downcast")
            return
        }
        dest.questionTypeReceived = questionType
    }

secondary VC

(次级VC)

    var questionTypeReceived:String = String()
    var answerTotalValue:Double = Double()
    var questionNumber:Int = Int()
    var questionBody = ""
    var questionType = ""

    let answerYesValue:Double = Double.random(in: 1...5)
    let answerNoValue:Double = Double.random(in: 0..<3)

        switch questionTypeReceived {

        case "Random":
            questionTypeReceived = "Random"
            questionsImageView.image = UIImage(named: randomImages.randomElement()!)
            let questionNumber = randomQuestions.keys.sorted()
            let questionBody = randomQuestions.values
            for (questionNumber, questionBody) in randomQuestions {
                questionTitleLabel.text = "Question #(questionNumber)"
                questionsTextLabel.text = questionBody
            }
        default: return
        }

    let randomQuestions: [Int : String] = [
        1: "Did you already agree to attend?",
        2: "Does it cost money to attend?",
        3: "Is it time consuming (4+ hours)?"
    ]

    @IBAction func yesButtonPressed(_ sender: UIButton) {
        answerTotalValue += answerYesValue
        print(answerTotalValue)
        print(questionTypeReceived)
    }


  ask by Eli McClellan translate from so

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

There seems to be some confusion on how to handle properties and local variables, you have for instance 1 property and 2 local variables named questionNumber and you are also iterating the whole dictionary when as I see it you only want one question.

(在如何处理属性和局部变量方面似乎有些混乱,例如,您有1个属性和2个名为questionNumber局部变量,并且您正在遍历整个字典,因为我看到它只想要一个问题。)

One way to get away from this and a solution that is also good for other reason like not doing everything in your controller class and separating responsibilities is to move the questions and handling of them into a separate struct or class.

(避免这种情况的解决方案以及因其他原因(例如,不执行控制器类中的所有工作并划分职责)而使解决方案也很好的一种方法是将问题移至单独的结构或类中。)

Let's create a Questions struct that holds the questions, keeps track of what questions has been asked and can deliver the next question to ask.

(让我们创建一个包含Questions结构,跟踪已提出的问题,并提供下一个要提出的问题。)

struct Questions {
    private randomQuestions: [Int : String] = [
        1: "Did you already agree to attend?",
        2: "Does it cost money to attend?",
        3: "Is it time consuming (4+ hours)?"
    ]

    private var questionIndex = 0

    mutating func nextQuestion() -> (number: Int, question: String?) {
        questionIndex += 1
        return (questionIndex, randomQuestions[questionIndex])
    }
}

Note the question mark for the string in the return tuple, if no questions exists for a index (questionIndex > 3) the question returned will be nil

(注意返回元组中字符串的问号,如果索引不存在任何问题(questionIndex> 3),则返回的问题为nil)

Then you can use it in you code like this, first declare it as a property in your VC

(然后可以在这样的代码中使用它,首先在VC中将其声明为属性)

var questions = Questions()

Then when getting the question

(然后当收到问题时)

switch questionTypeReceived {
case "Random":
    questionsImageView.image = UIImage(named: randomImages.randomElement()!)
    let nextQuestion = question.nextQuestion()
    if let question = nextQuestion.question {
        questionTitleLabel.text = "Question #(nextQuestion.number)"
        questionsTextLabel.text = question
    } else {
       // no more questions to ask, this needs to be handled
    }
default: return
}

So a little more work to write a new struct but your code in the VC becomes simpler and a lot of properties and variables are no longer needed.

(因此,编写新结构需要更多的工作,但是VC中的代码变得更简单,并且不再需要许多属性和变量。)


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...