How to parse Json object - iphone

I'm stuck at json object parsing really tried hard. The problem is how to parse the json object. Here's what i get the response in the log.
{"0":{"**title**":"Test Event","url_title":"test_event1","status":"open","entry_date":"Sep 10, 2012,
05:20:38AM","entry_id":"26","site_id":"1","channel_id":"3","field_dt_40":null,"field_dt_58":null,"channel_title":"News &
Events","channel_name":"news_events","start_date":"1348120800","end_date":"1348120800","start_time": "43200","end_time":"46800","where":"FCF","news_event_description":"<p>\n\tLunch with group.<\/p>\n"},
"1":{"**title**":"Test Event 2","url_title":"test_event_2","status":"open","entry_date":"Sep 10, 2012, 05:20:08AM","entry_id":"28","site_id":"1","channel_id":"3","field_dt_40":null,"field_dt_58":null,"channel_title":"News & Events","channel_name":"news_events","start_date":"1348207200","end_date":"1348207200","start_time":"43200","end_time":"46800","where":"FCF - Lunch","news_event_description":"<p>\n\tThis was a great event.<\/p>\n"},
"2":{"**title**":"Test Event 3","url_title":"test_event_3","status":"open","entry_date":"Sep 10, 2012, 05:20:54AM","entry_id":"29","site_id":"1","channel_id":"3","field_dt_40":null,"field_dt_58":null,"channel_title":"News & Events","channel_name":"news_events","start_date":"1346738400","end_date":"1346738400","start_time":"7200","end_time":"11700","where":"FCF - Lunch","news_event_description":"<p>\n\tFall planning season.<\/p>\n"}}
The problem is i want to show all the titles in the tableview. I can get the single Title by using key 0,1,2. But i want all the titles to be shown at once i parse
Please help me out guys, Thanks in advance.

Suppose jsonDict is your json dictionary.... Try this
NSArray * keys=[[NSArray alloc]init];
keys=[jsonDict allKeys];
NSMutableArray *titles=[[NSMutableArray alloc]init];
for(int i=0;i<[keys count];i++){
[titles addObject:[[jsonDict valueForKey:[keys objectAtIndex:i]]valueForKey:#"title"]];
}
NSLog(#"your array of titles : %#",titles); //use this array to fill your cell

Are you trying to parse the JSON yourself? You might find it easier to use something that's already well tested, such as TouchJSON or Apple's own NSJSONSerilization. The result should be a graph of Objective-C objects that you can use however you like.
In any case, what you've got there is the equivalent of a dictionary of dictionaries. If you have that as a NSDictionary called myJSONDictionary, you can say:
NSArray *theObjects = [myJSONDictionary allValues]; // gets all the objects
NSArray *theTitles = [theObjects valueForKey:#"**title**"]; // gets all the titles
You can also iterate through a dictionary using fast enumeration:
NSMutableArray *theTitles = [NSMutableArray array];
for (NSString *key in myJSONDictionary) {
NSDictionary *object = [myJSONDictionary objectForKey:key];
NSString *title = [object objectForKey:#"**title**"];
[theTitles addObject:title]
}
There's no real advantage to doing that instead of using KVC as in the first example if you just need the titles, but it could be the right choice if you have more complex work to do for each object.

Related

iPhone Programming - complex JSON Parsing - UITableView

Hey guys :) I am quite new to stack overflow and iPhone programming. I am trying to parse a complex JSON to display some stuff in the UITableView.
a part of the JSON structure -
{"1":{"1":"Ent1","done":"No"},"2":{"1":"Ent2","done":"No"}}
I am able to parse through the main keys "1" and "2" and able to grab the values corresponding to the key "1" inside {"1":"Ent1","done":"No"}, {"1":"Ent2","done":"No"} store them into a dictionary/ a string with the following code :
for (NSString *key in dict)
{
NSString *answer = [dict objectForKey:#"1"];
NSLog(#"%#", answer);
}
The result is Ent1 and Ent2 because the code iterates over the for loop and checks for the objects with key "1".
The problem is this - I want to store both the values(Ent1 and Ent2) into an array.
I use the following code:
NSMutableArray *array = [[NSMutableArray alloc] initWithObjects: answer, nil];
but it just takes the last index in the dictionary which is Ent2.
Could you please tell me how could I add both the values for key 1 into an array?
Thanks in advance :)
To add to jamapag's answer, you can also use JSON libraries in objective C which do all the work for you like SBJSON or YAJL, or even as part of the more recent versions of the mac/iOS SDKs, NSJSONSerialization.
NSMutableArray *array = [[NSMutableArray alloc] init];
for (NSString *key in dict)
{
NSString *answer = [dict objectForKey:key];
[array addObject:answer];
}

how to get objects from a json array in iphone?

I am working on an iPhone app which involves using json-framework.I am getting array using NSURL
[{"firstName":"X","lastName":"Y","id":1},{"firstName":"A","lastName":"B","id":2}]
How can i get these 2 objects as like if i query for id=1, the O/P is
id=1
firstName:X
lastName:Y
and putting it in a table.
I am googling the stuff from many days but didn't get any solution.
Please help me out , explanation through code is appreciated.
Thank You.
If your target SDK is ios4 or higher, you can use this project
https://github.com/stig/json-framework/
Once you add the source to your project, just
#import "SBJson.h"
and convert your Json string as follows
jsonResponse = [string JSONValue];
The method will fail if you don't have the full Json array in your string, but you can keep appending strings until it doesn't fail
To follow up for codejunkie's request below
you can assume in your data structure that the jsonResponse is an NSArray
In other implementations take care to test the response for NSArray or NSDictionary
NSArray * myPeople = [string JSONValue];
NSMutableDictionary * organizedData = [[NSMutableDictionary alloc] init];
for (NSDictionary * p in myPeople) {
[organizedData setValue:p forKey:[p valueForKey:#"id"]];
}
// now you can query for an id like so
// [organizedData valueForKey:#"1"]; and your output will be what you wanted from the original question
// just don't forget to release organizedData when you are done with it
https://github.com/johnezang/JSONKit
I use this to get data from a webservice that spits out 50 records each having another 20 internal elements similar to the one you specify...
I use the JSONKit in the following manner..(Had a look at SBJson a lot of user but i got confused from the word go.)
JSONDecoder *jArray = [[JSONDecoder alloc]init];
NSMutableArray *theObject = [[NSMutableArray alloc] init];
theObject = [jArray objectWithData:theResponseData];//objectWithString:theResponseString
NSMutableArray *csArray = [[NSMutableArray array] retain] ;
for(id key in theObject)
{
if([key valueForKey:#"firstName"] != Nil)
{
........
}
if([key valueForKey:#"lastName"] != Nil)
{
........
}
}
check it out and let me know if it works or not.. By the way Great responses guys... Good

iPhone: How to convert normal NSArray into an NSArray containing NSNumber values?

In my iPhone app, I am using an array which contains the values like shown below:
A:{
1000,
2000,
-1000,
4000
}
Now I want to convert this to the array shown below.
NSArray *A = [[NSArray alloc] initWithObjects:[NSNumber numberWithInt:1000],[NSNumber numberWithInt:2000],[NSNumber numberWithInt:-1000],[NSNumber numberWithInt:4000],nil];
How can I do that?
Edit:
Also I cannot use the value of Array A:{1000,2000,-1000,4000} to directly pass it into the NSNumber numberWithInt method, because it takes these values as NSString and not integers.
regarding to another question I saw from you I'm guessing those values are NSStrings
then use something like this.
NSMutableArray *array = [NSMutableArray array];
for (NSString *numberString in numberStringArray) {
[array addObject:[NSNumber numberWithInteger:[numberString integerValue]]];
}
and to be honest I think you should invest more time for the basics before you try to make use of core-plot

How can i get Original order of NSDictionary/NSMutableDictionary?

i have created NSMutableDictionary with 10 keys.Now i want to access NSMutableDictionary keys in a same order as it was added to NSMutableDictionary (using SetValue:* forKey:* );
How can i achieve that ?
If you absolutely must use a dictionary container, you have to use a key that is sortable by the order in which you add key-value pairs. Thus, when creating your dictionary, you use a key that is an auto-incrementing integer or similar. You can then sort on the (integer) keys and retrieve the values associated with those keys.
If you do all of that, however, you may as well just use an NSMutableArray and add values to the array directly! It will be much faster and require less code. You just retrieve objects in order:
for (id obj in myArray) { /* do stuff with obj... */ }
NSMutableDictionary can't do that. Take a look at e.g. Matt Gallaghers OrderedDictionary.
I wrote a quick method to take a source array (of objects that are all out of order) and a reference array (that has objects in a desired (and totally arbitrary) order), and returns an array where the items of the source array have been reorganized to match the reference array.
- (NSArray *) reorderArray:(NSArray *)sourceArray toArray:(NSArray *)referenceArray
{
NSMutableArray *returnArray = [[NSMutableArray alloc] init];
for (int i = 0; i < [referenceArray count]; i++)
{
if ([sourceArray containsObject:[referenceArray objectAtIndex:i]])
{
[returnArray addObject:[arrReference objectAtIndex:i]];
}
}
return [returnArray copy];
}
Note that this is very fragile. It uses NSArray's containsObject: method, which ultimately will call NSObject's isEqual:. Basically, it should work great for arrays of NSStrings, NSNumbers, and maybe NSDates (haven't tried that one yet), but outside of that, YMMV. I imagine if you tried to pass arrays of UITableViewCells or some other really complex object, it would totally sh*t itself, and either crash or return total garbage. Likewise if you were to do something like pass an array of NSDates as the reference array and an array of NSStrings as the source array. Also, if the source array contains items not covered in the reference array, they'll just get discarded. One could address some of these issues by adding a little extra code.
All that said, if you're trying to do something simple, it should work nicely. In your case, you could build up the reference array as you are looping through your setValue:forKey:.
NSMutableArray *referenceArray = [[NSMutableArray alloc] init];
NSMutableDictionary *yourDictionary = [[ NSMutableDictionary alloc] init];
for (//whatever you are looping through here)
{
[yourDictionary setValue://whatever forKey:key];
[referenceArray addObject:key];
}
Then, when you want to loop over your items in the order they came in, you just
for (NSString *key in [self reorderArray:[myDict allKeys] toArray:referenceArray])
Actually you have a reference array in order manner then why you have to add to one more array.So i guess this approach is not good.Please consider my opinion.
Although #GenralMike 's answer works a breeze, it could be optimized by leaving off the unnecessary code as follows:
1) Keep an array to hold reference to the dictionary keys in the order they are added.
NSMutableArray *referenceArray = [[NSMutableArray alloc] init];
NSMutableDictionary *yourDictionary = [[ NSMutableDictionary alloc] init];
for (id object in someArray) {
[yourDictionary setObject:object forKey:someKey];
[referenceArray addObject:someKey]; // add key to reference array
}
2) Now the "referenceArray" holds all of the keys in order, So you can retrieve objects from your dictionary in the same order as they were originally added to the dictionary.
for (NSString *key in referenceArray){
//get object from dictionary in order
id object = [yourDictionary objectForKey:key];
}

Looping through values in NSDictionary throws fault

I have a plist file that I am loading into an NSDictionary *setDictionary that contains a set of fields, pictureDesc1, pictureDesc2, etc.
Once the NSDictionary is loaded, I can retrieve a value using
[setDictionary objectForKey:#"pictureDesc1"];
But I cannot do a loop like this:
for (int i=1; i<=numberOfPictures; i++) {
NSString *keyName = [NSString stringWithFormat:#"pictureDesc%d",i];
NSString *description = [NSString stringWithFormat:#"%#", [setDictionary objectForKey:keyName]];
}
Is there a different way to dynamically call keys from within an NSDictionary?
If you keys fit a numerical pattern, then it would be easier and more robust to simply store them in a array. You could even store an array as a value in the dictionary with the key of "pictureDescription".
Then when you wanted to loop through them just use a simple numerical loop:
NSArray *pictArray=[setDictionary valueForKey:#"pictureDescription"];
NSString *description;
for (i=0;i<[pictArray count];i++){
description=[pictArray objectAtIndex:i];
//... do whatever
}
If you find yourself shoehorning the functionality of an array into a dictionary or vice versa you probably should back out and just use an array or dictionary in the first place. When using a dictionary, just use an enumerator to step through the values.