使用jQuery调用AJAX后,JSON数据消失

时间:2022-06-01 21:28:38

I'm making a quiz and trying to import questions from a JSON file. However when I import the questions and try to make use of them in my js file the data disappears. What am I doing wrong? Would appreciate some help =)!

我正在进行测验并尝试从JSON文件导入问题。但是,当我导入问题并尝试在我的js文件中使用它们时,数据就会消失。我究竟做错了什么?会感激一些帮助=)!

First I have a question object with properties:

首先,我有一个带有属性的问题对象:

function Question(question, choices, correctChoice, userAnswer, type) {

    this.question = question;
    this.choices = choices;
    this.correctChoice = correctChoice;
    this.userAnswer = userAnswer;
    this.type = type;

}

I want to import JSON data and turn that data into Question Objects:

我想导入JSON数据并将该数据转换为问题对象:

var allQuestions = [];
var category = "history";
var jsonData = null;

   function callJson(){

        $.ajax({
            url: 'myJsonUrl.json',
            dataType: 'json',

            success: function(data) {
                jsonData = data;
            }
        });  
   }

   $(".btn").click(function(){

       var jsonDataLength = 0; 

       for(var key in jsonData[category])
           jsonDataLength++;

       for(var i=0; i < jsonDataLength; i++) {
           allQuestions[i] = new Question();
           var questionNr = "q" + (i+1).toString();

           for(var properties in jsonData[category][questionNr])
               allQuestions[i][properties] = jsonData[category][questionNr][properties]; 
       }
    alert(allQuestions[0].question); //If i alert this here I get the correct value
    callJson();  
   });

Now if I try to use that data anywhere else outside the .btn the question object doesen't have any data:

现在,如果我尝试在.btn之外的任何其他地方使用该数据,那么问题对象就不会有任何数据:

$(".btn-show").on("click", function(){

    alert(allQuestions[0].question);    // This won't work    
});

Here's the JSON file:

这是JSON文件:

{ 
"history": {    

    "q1": {
        "question": "Which country did Britain fight in the War of Jenkins's Ear?",
        "choices": ["Norway", "India", "Spain", "Turkey"],
        "correctChoice": 2,
        "userAnswer": -1,
        "type": "radio"
    },

    "q2": {
        "question": "What was the largest naval battle of the First World War?",
        "choices": ["Battle of Poltava", "Battle of Jutland", "Battle of Stalingrad", "Battle of Hastings"],
        "correctChoice": 1,
        "userAnswer": -1,
        "type": "radio"
    },

    "q3": {
        "question": "In which year was Abraham Lincoln assassinated?",
        "choices": ["1915", "1755", "1805", "1865"],
        "correctChoice": 3,
        "userAnswer": -1,
        "type": "radio"
    },

    "q4": {
        "question": "Which countries formed the triple entente before the First World War?",
        "choices": ["Italy", "Britain", "France", "Germany", "Austria", "Russia"],
        "correctChoice": [-1, 1, 1, -1, -1, 1],
        "userAnswer": [],
        "type": "checkbox"
    }
}

}

2 个解决方案

#1


0  

It looks like the questions are not being loaded before you're calling for their value. Try this:

在你要求他们的价值之前,问题似乎没有被加载。尝试这个:

var allQuestions = [];
var category     = "history";
var jsonData     = null;

function populateQuestions(callback){
  $.ajax({
    url: 'myJsonUrl.json',
    dataType: 'json',

    success: function(data) {
      allQuestions = []; // kill off previous results
      jsonData     = data;

      var jsonDataLength = 0; 

      for (var key in jsonData[category]) {
          jsonDataLength++;
      }

      for (var i=0; i < jsonDataLength; i++) {
        allQuestions[i] = new Question();
        var questionNr = "q" + (i+1).toString();

        for(var properties in jsonData[category][questionNr]) {
          allQuestions[i][properties] = jsonData[category][questionNr][properties]; 
        }
      }

      // if a callback was passed, call it and pass in the questions
      if (typeof callback === 'function') {
          callback(allQuestions);
      }
    }
  }); 
 }

 $('.btn').click(populateQuestions).click();

This attaches the populateQuestions function to the click of the button and then fires it straight away.

这会将populateQuestions函数附加到单击按钮,然后立即将其触发。

You could do better than the last click handler too. You could call:

你也可以比最后一次点击处理程序做得更好。你可以打电话:

populateQuestions(functionToActuallyDoSomething);

With functionToActuallyDoSomething being a callback that is passed the fetched questions.

使用functionToActuallyDoSomething作为回调,传递提取的问题。

#2


-1  

True, because allQuestions is out of scope there. You could try passing it to the click like this:

是的,因为所有问题都超出了范围。您可以尝试将其传递给点击,如下所示:

$(".btn-show").on("click", function(allQuestions){
    alert(allQuestions[0].question); // This won't work    
});

#1


0  

It looks like the questions are not being loaded before you're calling for their value. Try this:

在你要求他们的价值之前,问题似乎没有被加载。尝试这个:

var allQuestions = [];
var category     = "history";
var jsonData     = null;

function populateQuestions(callback){
  $.ajax({
    url: 'myJsonUrl.json',
    dataType: 'json',

    success: function(data) {
      allQuestions = []; // kill off previous results
      jsonData     = data;

      var jsonDataLength = 0; 

      for (var key in jsonData[category]) {
          jsonDataLength++;
      }

      for (var i=0; i < jsonDataLength; i++) {
        allQuestions[i] = new Question();
        var questionNr = "q" + (i+1).toString();

        for(var properties in jsonData[category][questionNr]) {
          allQuestions[i][properties] = jsonData[category][questionNr][properties]; 
        }
      }

      // if a callback was passed, call it and pass in the questions
      if (typeof callback === 'function') {
          callback(allQuestions);
      }
    }
  }); 
 }

 $('.btn').click(populateQuestions).click();

This attaches the populateQuestions function to the click of the button and then fires it straight away.

这会将populateQuestions函数附加到单击按钮,然后立即将其触发。

You could do better than the last click handler too. You could call:

你也可以比最后一次点击处理程序做得更好。你可以打电话:

populateQuestions(functionToActuallyDoSomething);

With functionToActuallyDoSomething being a callback that is passed the fetched questions.

使用functionToActuallyDoSomething作为回调,传递提取的问题。

#2


-1  

True, because allQuestions is out of scope there. You could try passing it to the click like this:

是的,因为所有问题都超出了范围。您可以尝试将其传递给点击,如下所示:

$(".btn-show").on("click", function(allQuestions){
    alert(allQuestions[0].question); // This won't work    
});