2009-10-05 4 views
0

J'ai quelques questions concernant le code ci-dessous:Accéder à un tableau de dictionnaires?

(1) Est-ce que "newItem" est un objet autoreleased? Son obtenir un dictionnaire retourné à partir de l'index de tableau spécifié? (2) Existe-t-il un moyen simple d'accéder à un tableau de dictionnaires en une seule fois, ou est-ce que je le fais comme prévu?

#import <Foundation/Foundation.h> 

int main (int argc, const char * argv[]) { 
    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; 

    NSMutableArray *menu = [[NSMutableArray alloc] init]; 
    NSMutableDictionary *menuItem; 
    NSMutableDictionary *newItem; 

    NSArray *itemName = [NSArray arrayWithObjects: 
         @"Latte Medio", 
         @"Cappucion Medio", 
         @"Mocha Medio", 
         @"Vanilla Latte Medio",nil]; 

    NSArray *itemFat = [NSArray arrayWithObjects:  
         [NSNumber numberWithFloat:6.9], 
         [NSNumber numberWithFloat:4.7], 
         [NSNumber numberWithFloat:6.6], 
         [NSNumber numberWithFloat:6.9],nil]; 

    NSArray *itemCals = [NSArray arrayWithObjects: 
         [NSNumber numberWithInt:516], 
         [NSNumber numberWithInt:408], 
         [NSNumber numberWithInt:624], 
         [NSNumber numberWithInt:743],nil]; 

    NSLog(@"DICTARRAY ... Start"); 

    // Create menuItem object 
    menuItem = [[NSMutableDictionary alloc] init]; 
    [menuItem setObject:[itemName objectAtIndex:0] forKey:@"product"]; 
    [menuItem setObject:[itemFat objectAtIndex:0] forKey:@"fat"]; 
    [menuItem setObject:[itemCals objectAtIndex:0] forKey:@"calories"]; 

    // Add menuItem object to menu 
    [menu addObject:menuItem]; 
    [menuItem release], menuItem = nil; 

    // Access menu to get menuItem 
    newItem = [menu objectAtIndex:0]; 
    NSLog(@"DATA: %@",[newItem objectForKey:@"product"]); 
    NSLog(@"DATA: %@",[newItem objectForKey:@"fat"]); 
    NSLog(@"DATA: %@",[newItem objectForKey:@"calories"]); 

    // Clean up 
    [menu release], menu = nil; 
    [pool drain]; 
    return 0; 
} 

gary

+0

Le premier bit (où les tableaux sont initialisés) ne fait que configurer certaines données temporaires. La structure de données utilisée est un tableau d'objets de dictionnaire (j'imagine que j'aurais pu utiliser des objets personnalisés ici). – fuzzygoat

Répondre

7

La façon dont vous stockez ces informations semble étrange. Vous stockez tous les noms ensemble, tout le gros ensemble, et toutes les calories ensemble, quand vraiment les articles (ou objets) que vous traitez sont des boissons de café. Il serait probablement plus facile de faire un nouvel objet, disons CoffeeDrink, qui avait l'air quelque chose comme ce qui suit:

@interface CoffeeDrink:NSObject { 
    NSString *name; 
    NSNumber *fat; 
    NSNumber *calories; 
} 

@property(retain) NSString *name; 
@property(retain) NSNumber *fat; 
@property(retain) NSNumber *calories; 

@end 

Ensuite, dans votre code, vous pourriez avoir un NSArray de différentes CoffeeDrink s.

+0

merci pour le conseil, je vais essayer. – fuzzygoat

+2

C'est ce qu'on appelle un objet modèle, et il est absolument essentiel d'écrire une application Cocoa complète - non seulement pour des raisons de complexité, mais aussi parce que certaines choses, comme les liaisons et le support AppleScript, les exigent. Pour plus de détails sur la façon d'en créer un, lisez le Guide d'implémentation de l'objet modèle: http://developer.apple.com/mac/library/documentation/Cocoa/Conceptual/ModelObjects/ –

+0

Merci Peter, j'apprends encore le lanaguage et n'ont pas vraiment regardé au-delà des structures de données de base. Je vais certainement regarder le guide du modèle d'objet, merci beaucoup d'avoir pris le temps d'afficher un lien. – fuzzygoat

1

newItem n'est pas un objet autoreleased, il semble être un pointeur vers menuItem, qui n'est (également) pas libeleased. Je suppose que vous êtes obligé de stocker ces informations sous forme de tableaux pour une raison ou une autre, et que vous n'essayez pas délibérément de vous rendre la vie plus difficile. En ce sens, vous pouvez toujours simplifier les choses un peu.

Vous pourriez tout faire en ligne, mais cela deviendrait probablement "la ligne de code de l'enfer". Je serais probablement l'écrire est comme ça (pseudo-code)

NSMutableDictionary* childDictionary = // .. make the dictionary 

// for each NSArray a 
{ 
    NSString* k = // ... arbitrary key 
    NSArray* a = [NSArray arrayWithObjects:// ... make the array with objects]; 
    [childDictionary addObject:a forKey:k]; 
} 

// stuff it into the parent 
NSDictionary* parentDictionary = [NSDictionary withObjects:childDictionary, nil forKeys:@"root"]; 
+0

Votre droit en ce qui concerne menuItem est un pointeur vers un objet dans le NSMutableArray. Je me rends maintenant compte que ce n'est pas autoeleased, mais sera cependant nettoyé correctement lorsque je libère le tableau et tous les objets contenus sont également détruits. – fuzzygoat

+0

La structure de données est juste un test pour configurer un tableau de dictionnaires, j'imagine que j'aurais mieux mis en place un tableau d'objets personnalisés, ce qui est beaucoup plus logique d'être véridique. – fuzzygoat

-1

dans obj-c, les lignes directrices de la pomme sont, en général, lorsqu'une méthode/objet retourne un objet que vous devez éventuellement vous libérer, la méthode le nom commence par « nouveau », « copie », à savoir:

newArray 
copyArray 

lors de l'ajout des choses à un NSArray ou NSDictionary, ils se conservés et gérés par ces tableaux ou des dictionnaires. les éléments que vous y mettez recevront un message de libération lorsque vous libérerez le tableau ou le dictionnaire contenant vos éléments.

+0

Merci pxl, je réalise maintenant que je créais simplement un pointeur vers un objet existant. Donc ce n'est pas un problème car les objets du tableau seront libérés quand le tableau ira. – fuzzygoat

+0

> [. . .] ou le nom de l'objet, par exemple: > [. . .] arrayWithItems Ce dernier point est incorrect. '+ arrayWithItems:' devrait renvoyer un tableau autoreleased contenant les éléments fournis. Cette différence de propriété est la principale différence entre '[[NSArray alloc] init]' ou '[NSArray new]' et les méthodes de commodité telles que '[tableau NSArray]'. (Aussi, votre "ie" devrait être un "eg" car il introduit un exemple.) Utilisez "ie" quand vous pourriez écrire "c'est" et "eg" quand vous pourriez écrire "par exemple". utilisez "c'est" et "par exemple".) –

Questions connexes