Populating NSDictionary and NSArrays for Model data
-
06-12-2019 - |
Question
I'm trying to create an NSDictionary
full of arrays in the implementation file of my model but my code hasn't worked yet. I want to create arrays that are lists of types of dogs and cats and then add those arrays to a dictionary with keys called DOG
and CAT
. Here is my code:
@implementation wordDictionary
@synthesize catList = _catList;
@synthesize dogList = _dogList;
@synthesize standardDictionary =_standardDictionary;
- (void)setCatList:(NSMutableArray *)catList
{
self.catList = [NSMutableArray arrayWithObjects:@"lion", @"puma", @"snow leopard", nil];
}
- (void)setDogList:(NSMutableArray *)dogList
{
self.dogList = [NSMutableArray arrayWithObjects:@"pit bull", @"pug", @"chihuahua", nil];
}
-(void)setStandardDictionary:(NSMutableDictionary *)standardDictionary
{
[self.standardDictionary setObject: _catList forKey:@"CAT"];
[self.standardDictionary setObject: _dogList forKey:@"DOG"];
}
- (NSString*)selectKey
{
NSInteger keyCount = [[self.standardDictionary allKeys] count];
NSInteger randomKeyIndex = arc4random() % keyCount;
NSString *randomKey = [[self.standardDictionary allKeys] objectAtIndex:randomKeyIndex];
return randomKey;
}
@end
This code is the model. The model is hooked up to my view controller such that when a user taps a button, the NSString
returned from randomKey
is displayed in a label on the screen. So the text will read either CAT
or DOG
. Here's the code for that:
- (IBAction)changeGreeting:(UIButton*)sender {
NSString *chosenKey = [self.dictionary selectKey];
NSString *labelText = [[NSString alloc] initWithFormat:@"%@", chosenKey];
self.label.text = labelText;
}
Unfortunately when I tap the button on the simulator I get an error message saying: Thread 1:EXC_ARITHMETIC (code=EXC_1386_DIV, subcode=0x0)
at NSInteger randomKeyIndex = arc4random() % keyCount;
and it appears that I'm getting it because neither my NSArray
nor my NSDictionary
have any objects inside of them.
Does anyone have any idea why my NSArray
and NSDictionary
haven't been populated?
Thanks very much.
Solution
Assuming you called setCatList:
, setDogList:
and setStandardDictionary:
before. Probably that causing is this :
NSString *chosenKey = [self.dictionary selectKey];
change into this :
NSString *chosenKey = [self selectKey];
UPDATE
I'm trying to make your life easier. no need to create your object if you don't need the most.
- (NSMutableArray*)getCatList
{
return [NSMutableArray arrayWithObjects:@"lion", @"puma", @"snow leopard", nil];
}
- (NSMutableArray*)getDogList
{
return [NSMutableArray arrayWithObjects:@"pit bull", @"pug", @"chihuahua", nil];
}
-(NSMutableDictionary*)getStandardDictionary
{
NSMutableDictionary *standardDictionary = [NSMutableDictionary new];
[standardDictionary setObject:[self getCatList] forKey:@"CAT"];
[standardDictionary setObject:[self getDogList] forKey:@"DOG"];
return [standardDictionary autorelease];
}
- (NSString*)selectKey
{
NSMutableDictionary *standardDictionary = [self getStandardDictionary];
NSInteger keyCount = [[standardDictionary allKeys] count];
NSInteger randomKeyIndex = arc4random() % keyCount;
NSString *randomKey = [[standardDictionary allKeys] objectAtIndex:randomKeyIndex];
return randomKey;
}
- (IBAction)changeGreeting:(UIButton*)sender {
// NSString *chosenKey = [self selectKey];
//NSString *labelText = [[NSString alloc] initWithFormat:@"%@", chosenKey];
self.label.text = [self selectKey]; //no need to convert it to NSString again
}
OTHER TIPS
The simple answer is that there isn't any code here that calls the methods to set the arrays or dictionary.
But the real underlying issue is that there are a couple of bad 'patterns' going on here that you should fix:
In your setter methods (setCatList:, setDogList:, setStandardDictionary:) you're not setting the properties in question to the values that are passed in. For example, you should be setting catList to the passed in "catList" variable.
- (void)setCatList:(NSMutableArray *)catList
{
if (_catList != catList) {
[_catList release];
_catList = [catList retain];
}
}
Then you should have some kind of "setup" happening, usually in a method in the view controller like viewDidLoad:
[wordDictionary setCatList:[NSMutableArray arrayWithObjects:@"lion", @"puma", @"snow leopard", nil]];
// and more for the other two setters
Alternately, you can set these default values in the init for the wordDictionary class:
- (id)init {
self = [super init];
if (self) {
[self setCatList:[NSMutableArray arrayWithObjects:@"lion", @"puma", @"snow leopard", nil]];
}
return self;
}
The former is better in most cases, but you may have a good reason to pre-populate your model for all instances of the class.
Two things to consider:
I don't see you calling these:
setCatList:(NSMutableArray*)catList;
setDogList:(NSMutableArray*)dogList;
You use self.catList and self.dogList, but neither of those are synthesized, instead you have beatList and meList synthesized
Change the synthesizes to the catList and dogList, and make sure you call the set list methods, and then you should make some progress.