在iOS中解析json并将值添加到对象数组中

时间:2014-03-12 17:42:34

标签: ios arrays json parsing

我有以下json文件,我正在尝试从我的iOS应用程序解析它。我定义了一个解析文件的方法,但我不知道如何处理整数,即ID。我想将数据放在一个包含标题和一系列产品的数组(促销)中(下面将详细说明)。有什么建议或好的参考吗?

Json文件:

 "promotions": {
    "1": {
        "title": "promotion title",
        "product": {
            "1": {
                "title": "product title",
                "description": "this is the description"
            },
            "2": {
                "title": "product title",
                "description": "this is the description"
            }
          }
      },
    "2": { "3": {
                "title": "product title",
                "description": "this is the description"
            },
            "4": {
                "title": "product title",
                "description": "this is the description"
            }
         }
      } 
   }

这些是我的数据类:

Promotion { NSString *title; NSArray *products;}
Product { NSString *title; NSString *description;}

我的功能是加载json并在促销数组中添加所有对象,其中包含每个促销的一系列产品。

- (NSArray *) infoFromJSON{
    NSURL *url=[NSURL URLWithString:urlJSON];

    NSURLRequest *request = [NSURLRequest requestWithURL:url
                                             cachePolicy:NSURLRequestReloadIgnoringLocalAndRemoteCacheData
                                         timeoutInterval:30.0];
    NSURLResponse *response;
    NSData *data = [NSURLConnection sendSynchronousRequest:request returningResponse:&response error:nil];

    NSDictionary *jsonDictionary = [NSJSONSerialization JSONObjectWithData:data options:0 error:nil];

    NSMutableArray *promotions = [[NSMutableArray alloc] init];

    NSArray *array = [jsonDictionary objectForKey:@"promotions"];
    NSLog(@"array: %@", array);
    NSLog(@"items en array %d", [array count]);
    NSLog(@"object 1 en array: %@", [array objectAtIndex:1]);

    // Iterate through the array of dictionaries
    for(NSDictionary *dict in array) {
        Promotion *promotion= [[Promotion alloc] initWithJSONDictionary:dict];
        // Add the promotion object to the array
        [promotions  addObject:promotions];

        //Add the products to each promotion??
    }

    // Return the array of promotion objects
    return promotions;

}

3 个答案:

答案 0 :(得分:6)

您的JSON定义不明确,您必须尝试使用​​以下内容:

[{"promotion_id": 1
  "title": "promotion title", 
  "products": [{"product_id": 1, 
                "title": "product title", 
                "description": "this is the description"
               },
               {"product_id": 2, 
                "title": "product title", 
                "description": "this is the description"
               },
               ...
              ]
 },
 {"promotion_id": 2
  "title": "promotion title", 
  "products": [{"product_id": 3, 
                "title": "product title", 
                "description": "this is the description"
               },
               {"product_id": 4, 
                "title": "product title", 
                "description": "this is the description"
               },
               ...
              ]
 },
 ...
]

然后,要将JSON词典解析为自定义对象,我建议您使用我最近一直在工作的类别NSObject+Motis。将JSON字典映射到自定义Objective-C对象非常有用。

主要是,你必须这样做:

@interface Promotion : NSObject
@property (nonatomic, assing) NSInteger promotionId; 
@property (nonatomic, strong) NSString *title;
@property (nonatomic, strong) NSArray *products;
@end

@implementation Promotion
- (NSDictionary*)mjz_motisMapping
{
    return @{@"promotion_id" : @"promotionId",
             @"title" : @"title",
             @"products" : @"products",
            };
}

- (NSDictionary*)mjz_arrayClassTypeMappingForAutomaticValidation
{
    return @{"products": [Product class]};
}

@end

@interface Product : NSObject
@property (nonatomic, assing) NSInteger productId; 
@property (nonatomic, strong) NSString *title;
@property (nonatomic, strong) NSArray *productDescription;
@end

@implementation Promotion
- (NSDictionary*)mjz_motisMapping
{
    return @{@"product_id" : @"productId",
             @"title" : @"title",
             @"description" : @"productDescription",
            };
}
@end

然后执行解析:

- (void)parseTest
{
    NSData *data = jsonData; // <-- YOUR JSON data 

    // Converting JSON data into array of dictionaries.
    NSError *error = nil;
    NSArray *jsonArray = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:&error];

    if (error)
        return; // <--- If error abort.

    NSMutableArray *promotions = [NSMutableArray array];
    for (NSDictionary *dict in jsonArray)
    {
        Promotion *promotion = [[Promotion alloc] init];
        [promotion mjz_setValuesForKeysWithDictionary:dict];
        [promotions addObject:promotion];
    }
}

您可以在这篇文章中阅读它的工作原理:http://blog.mobilejazz.cat/ios-using-kvc-to-parse-json

希望它对你有所帮助。

答案 1 :(得分:1)

令人讨厌的JSON。如果可以,请改变它。目前你有很多字典,字典中的键是数字。这些词典应该是数组。

您已将代码编写为数组。

如果你需要保留JSON,请读出字典然后迭代密钥,或者,如果可以(因为你没有使用密钥进行排序),只需将所有值作为一个数组从字典并迭代它。

理想情况下,更改JSON并使用RestKit ...

答案 2 :(得分:0)

我终于最终改变了json:

{
    "promotions": [
        {
            "id": "1",
            "title": "promotion title",
            "products": [
                {
                    "id": "1",
                    "title": "product title",
                    "description": "description"
                },
                {
                    "id": "2",
                    "title": "product title",
                    "description": "description"
                }
            ]
        },
        {
            "id": "2",
            "title": "promotion title",
            "products": [
                {
                    "id": "6",
                    "title": "product title",
                    "description": "description"
                }
            ]
        }
    ]
}

这就是我解析json的方式:

- (NSArray *) infoFromJSON{
    // Create a NSURLRequest with the given URL
    NSURL *url=[NSURL URLWithString:urlJSON];

    NSURLRequest *request = [NSURLRequest requestWithURL:url
                                             cachePolicy:NSURLRequestReloadIgnoringLocalAndRemoteCacheData
                                         timeoutInterval:30.0];
    // Get the data
    NSURLResponse *response;
    NSData *data = [NSURLConnection sendSynchronousRequest:request returningResponse:&response error:nil];

    //Create an array to hold all the information
    NSMutableArray *info = [[NSMutableArray alloc] init];

    // Now create a NSDictionary from the JSON data
    NSDictionary *jsonDictionary = [NSJSONSerialization JSONObjectWithData:data options:0 error:nil];

    NSArray *arrayPromotions = [jsonDictionary objectForKey:@"promotions"];

    for(NSDictionary *dictCategories in arrayPromotions) {
        Block *promotion = [[Block alloc] initWithJSONDictionary:dictCategories];

        NSArray *arrayProducts = [dictCategories objectForKey:@"products"];

        promotion.questions = [[NSMutableArray alloc] init];
        for(NSDictionary *dictProducts in arrayProducts) {
            Product *product = [[Product alloc] initWithJSONDictionary:dictProducts];
            NSLog(@"product title %@", product.title);
            [promotions.product addObject:product];
        }

        [info addObject:promotion];
        NSLog(@"Promotion: %@ product 2: %@", promotion.title, [[promotion.products objectAtIndex:1] title]);
    }

    // Return the array of Location objects
    return info;

}

我在两个数据类(Promotion和Product)中定义并实现了initWithJSONDictionary方法

- (id)initWithJSONDictionary:(NSDictionary *)jsonDictionary {    
    if(self = [self init]) {
        self.title = [jsonDictionary objectForKey:@"title"];
    }
    return self;
}