Friday, September 2, 2011

Adding the *real* answers

So, yesterday we got to the point where we *almost* had random answers being displayed to our kanji-based word/question. The only problem is were were displaying kanji, instead of the kana, in the answers. So, here, we'll just start make sure to add the answers (i.e., hiragana) - along with the english translation - when we read the vocabulary entry.

So, we can quickly go to the code where the vocabulary entry gets loaded.
             
                NSString *kanji = [[NSString alloc] initWithUTF8String:(const char *) sqlite3_column_text(statement, 0)];
           
                NSString *hiragana = [[NSString alloc] initWithUTF8String:(const char *) sqlite3_column_text(statement, 1)];
           
                NSString *english = [[NSString alloc] initWithUTF8String:(const char *) sqlite3_column_text(statement, 2)];
           
                // NSLog(@"kanji: %@, hiragana: %@, english: %@", kanji, hiragana, english);
           
                // allocate the question
                question = [[Question alloc] init];
                question.number = cntr_question;
                question.questionTxt = kanji;
                // add the correct answer after converting it to an int
                question.correctAnswer = 1;
It looks like there's a problem - no hiragana or english are added. We'll remedy that by adding those two fields to question and loading them from the db.

Good, ok - now we have this:


#import <Foundation/Foundation.h>
#import "AppState.h"
@interface Question : NSObject {
NSString *questionTxt;
    NSString *hiragana;
NSString *english;
int correctAnswer;
int number;
 
// this will contain the hash table of questions_answer objects
NSMutableDictionary *answerHash;
}

@property (nonatomic, retain) NSString * questionTxt;
@property (nonatomic, retain) NSString * hiragana;
@property (nonatomic) int english;
@property (nonatomic) int number;
@property (nonatomic, retain) NSMutableDictionary *answerHash;
- (NSMutableArray *)    answerArray;
- (NSMutableArray *)    getAnswerArray : (AppState *) appState;
- (void) printDescription;
- (void) printAnswers;
- (NSString *) correctAnswerText;

@end
Ok, now we also probably need to add a synthesize in the implementation. 
@synthesize questionTxt, correctAnswer, number, answerHash, english, hiragana;
Ok, what next? Obviously, we need to load them up...

                question.number      = cntr_question;
                question.questionTxt = kanji;
                question.hiragana    = hiragana;
                question.english     = english;
Ok; now we can choose our multiple choices from among the hiragana instead of the kanji representation.

- (NSMutableArray *) getAnswerArray : (AppState *) appState
{
    NSDictionary *questionHash = [appState questionHash];
  
    NSArray *tempArray = [questionHash allKeys];
  
    int size = [tempArray count];  
  
// create array
NSMutableArray *answers = [[NSMutableArray alloc] init];  
    for (int i = 0; i < 4 ; i++) {
      
     
        // Get random value between 0 and number of questions
        int rand = arc4random() % (size - 1); // starts at zero, not 1        rand++; // between 1 and size
      
         NSNumber *key = [NSNumber numberWithInt:rand];
      
        Question *question  =       [questionHash objectForKey:key];
      
        NSString *answer = [question hiragana];  // <<< coming from hiragana
      
/* NSLog(@"answer is: %@",  answer); */
[answers addObject:answer];
}
return answers;
Let's take a look....

Ah better. Note the answers are now in hiragana.




However - the correct answer isn't there!

Let's remedy that by getting an random number between 1 and for (or 0 and 3, let's figure that one out) and plugging in the current question's hiragana:

Ok, after we initialize the answers in the QuestionController, all we have to do is throw the current anser somewhere in the answer array. Here's the definition of the answer array:


NSMutableArray *answers;

So, let's get a random number between zero and 3. We did got a random number in the getAnswerArray method:

Ok, this should do it:

 int rand = arc4random() % 3; // get a number between 0 and 3
  


Now, all we have to do is figure out how to stuff the real pronunciation into the answers array. Let's check out the getAnswerArray method again, which created the array in the first place:


[answers addObject:answer];

Doh! That's not going to help. Let's look up NSMutableArray: 

Ah, this looks a little bit more promising:
insertObject:atIndex:
Inserts a given object into the array's contents at a given index.
How does this look:


    int rand = arc4random() % 3; // get a number between 0 and 3   
    [answers insertObject:[currentQuestion hiragana] atIndex:rand];

 Let's run it...

Not bad, but it appears we need to remove something first, because now there are 5 entries, including the correct one:


So, let's try this:


    [answers removeObjectAtIndex: rand];    [answers insertObject:[currentQuestion hiragana] atIndex:rand];

Ah, much better:


Now, the only remaining question is, why do is this code doubled? It currently needs to appear in two methods: viewDidLoad and viewWillAppear. I think one might be called the first time, and the next called when it comes back from the "answer" view - but let's test it. It may be getting called twice - it looked like that might have been happening before.

Ok - it looks like we can get rid of it from the on did load with no consequences. Great!

In the next session, we'll do fun stuff like randomizing the sequence of questions and matching the real correct answer.




No comments:

Post a Comment