This function is intended to get a JSON and make an array of objects based on the object sent as parameter:
+ (NSArray *)Object: (id) object FromJSON:(NSData *)objectNotation error:(NSError **)error
{
NSError *localError = nil;
NSArray *parsedObject = [NSJSONSerialization JSONObjectWithData:objectNotation options:0 error:&localError];
if (localError != nil) {
*error = localError;
return nil;
}
NSMutableArray *output = [[NSMutableArray alloc] init];
NSArray *results = [parsedObject valueForKey:#"results"];
NSLog(#"Count %lu", (unsigned long)results.count);
for (NSArray *eventDic in results) {
object = [[[object class] alloc] init];
for (NSString *key in eventDic) {
if ([object respondsToSelector:NSSelectorFromString(key)]) {
[object setValue:[eventDic valueForKey:key] forKey:key];
}
}
[output addObject:object];
}
return output;
}
But it is crashing every time I run it. I get this error:
*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[NSNull countByEnumeratingWithState:objects:count:]: unrecognized selector sent to instance 0x1100c3ce0'
I am new to iOS programming and have no idea what this means.
NSArray *parsedObject = [NSJSONSerialization JSONObjectWithData:objectNotation options:0 error:&localError];
Pass 0 if you don't care about the readability of the generated string
if you want to parsed object as NSArray, change your options as NSJSONReadingMutableContainers
NSDictionary *dic_JSON = [NSJSONSerialization JSONObjectWithData: jsonData
options: NSJSONReadingMutableContainers
error: &error];
Related
Can someone please help me in parsing the below jsonData into a nsDictionary object
[ { "id": "22144" ,"t" : "AAPL" ,"e" : "NASDAQ" ,"l" : "111.57"
,"l_fix" : "111.57" ,"l_cur" : "111.57" ,"s": "2" ,"ltt":"4:00PM EST"
,"lt" : "Nov 28, 4:00PM EST" ,"lt_dts" : "2016-11-28T16:00:01Z" ,"c" :
"-0.22" ,"c_fix" : "-0.22" ,"cp" : "-0.20" ,"cp_fix" : "-0.20" ,"ccol"
: "chr" ,"pcls_fix" : "111.79" ,"el": "111.56" ,"el_fix": "111.56"
,"el_cur": "111.56" ,"elt" : "Nov 28, 8:00PM EST" ,"ec" : "-0.01"
,"ec_fix" : "-0.01" ,"ecp" : "-0.01" ,"ecp_fix" : "-0.01" ,"eccol" :
"chr" ,"div" : "0.57" ,"yld" : "2.04" } ]
#define QUERY_PREFIX #"https://www.google.com/finance/info?q=NSE:AAPL"
#define QUERY_SUFFIX #"NSE:AAPL"
#implementation YQL
- (NSDictionary *) query: (NSString *)statement {
NSString *query = [NSString stringWithFormat:#"%#%#%#", QUERY_PREFIX, [statement stringByAddingPercentEscapesUsingEncoding:NSASCIIStringEncoding], QUERY_SUFFIX];
NSData *jsonData = [[NSString stringWithContentsOfURL:[NSURL URLWithString:query] encoding:NSUTF8StringEncoding error:nil] dataUsingEncoding:NSUTF8StringEncoding];
NSString *dataString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
NSUInteger firstCurlyBracePos = [dataString rangeOfString:#"[" options:0].location;
NSUInteger lastCurlyBracePos = [dataString rangeOfString:#"]" options: NSBackwardsSearch].location;
NSString *jsonString = nil;
if(firstCurlyBracePos != NSNotFound && lastCurlyBracePos != NSNotFound) {
jsonString = [dataString substringWithRange:NSMakeRange(firstCurlyBracePos, (lastCurlyBracePos-firstCurlyBracePos)+1)];
}
NSData *someData = [jsonString dataUsingEncoding:NSUTF8StringEncoding];
NSLog(#"%# Nirmal",jsonString);
NSError *error = nil;
NSDictionary *results = [NSJSONSerialization JSONObjectWithData:someData options:0 error:&error];
NSLog(#"%# Anand",results);
NSString* latestLoans = [results objectForKey:#"el_cur"];
NSLog(#"loans: %#", latestLoans);
if (error) NSLog(#"[%# %#] JSON error: %#", NSStringFromClass([self class]), NSStringFromSelector(_cmd), error.localizedDescription);
return results;
}
#end
Terminating app due to uncaught exception
'NSInvalidArgumentException', reason: '-[__NSSingleObjectArrayI
objectForKey:]: unrecognized selector sent to instance 0x61800000d010'
The JSON you're trying to parse is an array, not an object, as denoted by the enclosing square brackets. So NSJSONSerialization is going to return an NSArray here, not an NSDictionary. Since it seems like there is only one object in this array, you can access it like so:
NSArray *results = [NSJSONSerialization JSONObjectWithData:someData options:0 error:&error];
NSDictionary *object = results.firstObject;
NSString *latestLoans = object["el_cur"];
I am new to iOS development. I am trying to covert JSOn array values to Objective-C values. My JSON values are like this:
{"result":
[{"alternative":
[{"transcript":"4"},
{"transcript":"four"},
{"transcript":"so"},
{"transcript":"who"}],
"final":true}],
"result_index":0}
I have tried it this way:
NSData *data = [NSData dataWithContentsOfURL:[NSURL URLWithString:speechrequestString]];
NSError *error;
NSDictionary *speechResult= [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&error];
NSArray *speechArray= [speechResult valueForKey:#"result"];
NSLog(#"%#",speechArray);
NSLog(#"Response is of type: %#", [speechArray class]);
speechArray is always null. How to resolvee this problem?
At the same time I would like to print transcript values.
I think the problem might be in initializing the array and Dictionary.
Try doing this,
NSDictionary *speechResult = [NSDictionary new];
NSArray *speechArray = [NSArray new];
Hope it helps..
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:data options:0 error:&error];//data is your response from server as NSData
if ([json isKindOfClass:[NSDictionary class]]){ //Added instrospection as suggested in comment.
NSArray * speechArray = json[#"result"];
}
NSLog(#"speech array %#",speechArray);
Did you check the value in NSDictionary (speechResult).
If it is nil, check the json data isValid or not.
NSError *error;
if ([NSJSONSerialization JSONObjectWithData:data
options:kNilOptions
error:&error] == nil)
{
// Check the error here
}else {
// here check whether it is a dictionary and it has key like #Bhadresh Mulsaniya mentioned.
}
If returns nil, then you check the error to understand what's wrong.
try this may be it will help you:-
NSData *data = [NSData dataWithContentsOfURL:[NSURL URLWithString:speechrequestString]];
NSError *error;
NSDictionary *speechResult = [NSDictionary new];
speechResult= [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&error];
NSArray *speechArray = [[NSArray alloc]init];
speechArray= [speechResult valueForKey:#"result"];
NSLog(#"%#",speechArray);
NSLog(#"Response is of type: %#", [speechArray class]);
try this code,
restaurantdictionary = [NSJSONSerialization JSONObjectWithData:mutableData options:NSJSONReadingMutableContainers error:&e];
NSMutableArray *main_array=[[NSMutableArray alloc]init];
main_array=[restaurantdictionary valueForKey:#"results"];
NSLog(#"main_array %#", main_array);
its working for me, hope its helpful
You have to initialize the array before using it,
NSData *data = [NSData dataWithContentsOfURL:[NSURL URLWithString:speechrequestString]];
NSError *error;
NSDictionary *speechResult= [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&error];
NSArray *speechArray= [[NSArray alloc] init];
speechArray= [speechResult valueForKey:#"result"];
if (speechArray.count>0) {
NSDictionary * alternativeDictn = [speechArray objectAtIndex:0];
NSArray *alternativeAry= [[NSArray alloc] init];
alternativeAry = [alternativeDictn objectForKey:#"alternative"];
NSLog(#"%#",alternativeAry);
}
NSLog(#"Response is of type: %#", [speechArray class]);
Using this code you will get following result,
(
{
transcript = 4;
},
{
transcript = four;
},
{
transcript = so;
},
{
transcript = who;
}
)
Try out the below code to get the transcripts:
NSData* jsonData = [yourJsonString dataUsingEncoding:NSUTF8StringEncoding];
NSError *error = nil;
NSDictionary *responseObj = [NSJSONSerialization
JSONObjectWithData:jsonData
options:0
error:&error];
if(! error) {
NSArray *responseArray = [responseObj objectForKey:#"result"];
for (NSDictionary *alternative in responseArray) {
NSArray *altArray = [alternative objectForKey:#"alternative"];
for (NSDictionary *transcript in altArray) {
NSLog(#"transcript : %#",[transcript objectForKey:#"transcript"]);
}
}
} else {
NSLog(#"Error in parsing JSON");
}
You should alloc your dictionary first like this-
NSDictionary *speechResult = [[NSDictionary alloc]init];
speechResult= [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&error];
NSArray *speechArray = [[NSArray alloc]init];
speechArray= [speechResult valueForKey:#"result"];
I am trying to develop an app that parses json data. I have the following json :
{
myobject:[
{
id:184,
title: "test title"
}
]
}
I have the following code which im trying to get the title data from this json
NSData *jsonData = [NSData dataWithContentsOfURL:myURL];
NSError *error = nil;
NSDictionary *currentObject = [NSJSONSerialization JSONObjectWithData:jsonData options:0 error:&error];
if(error)
{
NSLog(#"%#",error);
}
NSDictionary *nar = [currentObject objectForKey:#"myobject"];
NSLog(#"%#",[nar valueForKey:#"title"]);
NSString *curTitle = [nar valueForKey:#"title"];
self.myTitle.text = curTitle;
When I log the title, I can see that the title is indeed coming back. However, when I try to set the myTitle.text I get the following error
Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[__NSArrayI length]: unrecognized selector sent to instance 0x15631850
In your json my object field is not a dictionary, but array of dictionaries, so [nar valueForKey:#"title"] will return array of valueForKey for each of elements in that array.
If you're sure about data format you can extract string value from it the following way:
NSArray *nar = [currentObject objectForKey:#"myobject"];
NSString *curTitle = nar[0][#"title"];
But of course it is better to add some data validation/error handling in production code.
It is crash because Your dictionary contain NSArray, not dictionary.
NSArray *ar = [currentObject objectForKey:#"myobject"];
for(NSDictionary *dict in ar)
{
NSLog(#"%#", [dict objectForKey:#"title"];
)
}
NSString *curTitle = [[ar objectAtIndex:0] objectForKey:#"title"];
self.myTitle.text = curTitle;
You are trying to assign NSArray to self.myTitle.text.
NSData *jsonData = [NSData dataWithContentsOfURL:myURL];
NSError *error = nil;
NSDictionary *currentObject = [NSJSONSerialization JSONObjectWithData:jsonData options:0 error:&error];
if(error)
{
NSLog(#"%#",error);
}
NSArray *nar = [currentObject objectForKey:#"myobject"];
NSString *title = [[nar objectAtIndex:0] objectForKey:#"title"];
NSLog(#"%#",title);
self.myTitle.text = title;
I'm trying to create a JSON object that looks like this:
{ "request_type":"send_string" "security_level":0 "device_type":"ios" "blob":{"string":"blah"}"}
Here's my attempt:
NSDictionary *blobData = [NSDictionary dictionaryWithObjectsAndKeys:
sendString,#"string",
nil];
NSString *blobString = [[NSString alloc]
initWithData:[NSJSONSerialization dataWithJSONObject:blobData options:kNilOptions error:&error]
encoding:NSUTF8StringEncoding];
NSLog(#"Blob Created: %#", blobString);
NSDictionary *requestData = [NSDictionary dictionaryWithObjectsAndKeys:
#"send_string",#"request_type",
0,#"security_level",
#"ios",#"device_type",
//No Email Provided, This is just for testing
blobString,#"blob",
nil];
NSData *JSONRequestData = NULL;
if ([NSJSONSerialization isValidJSONObject:requestData]) {
NSLog(#"Proper JSON Object");
JSONRequestData = [NSJSONSerialization dataWithJSONObject:requestData options:kNilOptions error:&error];
}
else {
NSLog(#"requestData was not a proper JSON object");
return FALSE;
}
NSLog(#"%#",[[error userInfo] objectForKey:#"NSDebugDescription"]);
NSLog(#"%#",[[NSString alloc] initWithData:JSONRequestData encoding:NSUTF8StringEncoding]);
The problem is, that last NSLog tells me all I've created is something like this:
{"request_type":"send_string"}
So when I go and try to write this to the server with
[NSJSONSerialization writeJSONObject:JSONRequestData toStream:outputStream options:0 error:&error];
I get this error from the console:
*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '*** +[NSJSONSerialization writeJSONObject:toStream:options:error:]: Invalid top-level type in JSON write'
Replace this line
0,#"security_level"
with
[NSNumber numberWithInt:0],#"security_level"
This is really very odd.
We're accessing a json Twitter API that always returns an array.
ie
https://twitter.com/statuses/user_timeline/485963081.json
We do:
if([NSJSONSerialization class]) {
NSError *error = nil;
jsonResponse = [NSJSONSerialization JSONObjectWithData:responseData options:0 error:&error];
DLog(#"JSON Parsing Error: %#", error);
} else {
NSString * jsonString = [[NSString alloc] initWithData:responseData encoding:NSUTF8StringEncoding];
jsonResponse = [jsonString JSONValue];
}
if([jsonResponse count] > 0) {
NSString *jsonText = [[jsonResponse objectAtIndex:0] objectForKey:#"text"];
twitterText = jsonText;
}
This works a vast majority of the time. The rest, we get this:
[__NSCFDictionary objectAtIndex:]: unrecognized selector sent to instance
Note, all the errors are on iOS5, so the SBJSON library does not apply.
Sometimes NSJSONSerialization parses the array as a dict. Which frankly, is not possible using the data from twitter. So what's happening here?