Получить одно конкретное значение от JSON
Как и следовало ожидать, я довольно плохо знаком с obj-C и постоянно пытаюсь накопить знания и опыт. Но я все еще борюсь со многими концепциями, и это включает в себя "отлов" данных JSON. Я видел много учебников и руководств, но я просто не могу перевести их на то, что мне нужно. Большую часть времени они размещают данные в массивах или получают несколько значений и (конечно) используют разные переменные, что делает все запутанным и неясным для меня, хотя это должно быть глупо просто.
Я пытаюсь сделать что-то очень простое: получить единственное значение из открытого API погоды, температуру.
Я покажу вам мой код, который, по моим позорным знаниям, должен быть идеальным, но, видимо, он не работает:D
@implementation HomeViewController
{
NSMutableArray *tableData;
NSDictionary *jsonDict;
NSMutableString *title;
}
-(void) viewDidLoad
{
[super viewDidLoad];
NSError *error;
//I create my data array and the string i'll store my value later on
tableData = [[NSMutableArray alloc] init];
title = [[NSMutableString alloc]init];
// Creating the link for the json api so it fits coordinates ; this works but i edited the locations out to clear the code
NSString *s = [[NSString alloc]initWithFormat:@"http://api.openweathermap.org/data/2.5/weather?lat=%.05f&lon=%.05f", _annotation.coordinate.latitude, _annotation.coordinate.longitude];
// I go online and catch the data of the url stored in S
NSData *jSonData = [NSData dataWithContentsOfURL:[NSURL URLWithString:s]];
// This is a dictionary where all my data is stored from jsonData, keys and values all the way
jsonDict = [NSJSONSerialization JSONObjectWithData:jSonData options:NSJSONReadingMutableContainers error:&error];
// I use the string created previously and assign it the value stored in that dictionary, in the TEMP 'folder', right under MAIN.
title = [[jsonDict objectForKey:@"main"]objectForKey:@"main.temp"];
// I assign that title to a label so it appears in my view.
self.tempLabel.text = title;
...
}
Вот и ты. Я, вероятно, упускаю что-то очень простое, но я застрял в этом, и даже если я чувствую, что знаю, что делаю, я, вероятно, что-то упускаю. Так что было бы замечательно, если бы ответом, который вы мне дали, вы также могли бы сказать, что я сделал не так:D
Большое спасибо за вашу поддержку и знания. Это сообщество удивительно:)
3 ответа
Установите точку останова после присвоения значения jsonDict
и использовать
po jsonDict
в консоли, чтобы распечатать, что вы получаете. Затем настройте код, который извлекает значение. И используйте для этого современный синтаксис Objective-C.
пример
title = jsonDict[@"main"][@"temp"];
Заметка
po
команда отладчика, которая распечатывает содержимое объекта Если вам нужно распечатать содержимое примитива, используйте p
вместо.
Мое предположение
jsonDict = [NSJSONSerialization JSONObjectWithData:jSonData options:NSJSONReadingMutableContainers error:&error];
пытается создать nsdictionary, но результаты возвращаются в виде массива. Попробуй это:
NSError *e = nil;
NSArray *jsonArray = [NSJSONSerialization JSONObjectWithData: jsonDict options: NSJSONReadingMutableContainers error: &e];
if (!jsonArray) {
NSLog(@"Error parsing JSON: %@", e);
} else {
for(NSDictionary *item in jsonArray) {
NSLog(@"Item: %@", item);
}
}
Это должно установить вас правильно:
title = [[jsonDict objectForKey:@"main"]objectForKey:@"temp"];
Чтобы объяснить проблему, кажется, вы имели в виду temp
используя комбинацию точечного синтаксиса в ключе.
РЕДАКТИРОВАТЬ: В ответ на вашу ошибку:
Эта ошибка появляется, когда вы пытаетесь найти длину строки в значении, которое не относится к типу NSString. Похоже temp
возвращается как число. Таким образом, чтобы сделать то, что вы пытаетесь сделать, вы хотите преобразовать [[jsonDict objectForKey:@"main"]objectForKey:@"temp"]
к NSString:
NSNumber *temp = [[jsonDict objectForKey:@"main"]objectForKey:@"temp"];
NSString *tempString = [temp stringValue];
ИЛИ ЖЕ
NSString *temp = [[[jsonDict objectForKey:@"main"]objectForKey:@"temp"] stringValue];
Это позволит вам получить length
: temp.length
** РЕДАКТИРОВАТЬ: Если вы не пытаетесь получить длину массива данных о погоде... в этом случае я хотел бы увидеть больше этого кода