JSON file in arrays - ios

I'm trying to parse this JSON :
[
{
"text" : "Test",
"color" : "yellow",
},
{
"text" : "Test2",
"color" : "blue",
},
]
I am trying to get two arrays, one with the key "text" and another with the key "color".
NSString *jsonPath = [[NSBundle mainBundle] pathForResource:#"notes"
ofType:#"json"];
NSError *e = nil;
NSData *data = [[NSData alloc] initWithContentsOfFile:jsonPath];
NSArray *parsed = [NSJSONSerialization JSONObjectWithData:data
options:NSJSONReadingMutableContainers
error:&e];
if (! [parsed isKindOfClass:[NSArray class]]) {
NSLog(#"Error");
}
NSArray *texts = [[NSMutableArray alloc] init];
NSArray *colors = [[NSMutableArray alloc] init];
for (NSDictionary* dict in parsed)
{
[texts addObject:dict [#"text"]];
[colors addObject:dict [#"color"]];
}
I have an error with the following code:
[texts addObject:dict [#"text"]];
[colors addObject:dict [#"color"]];
How should I fix this?

Looking at your JSON data, you've got an array that contains 2 dictionaries. Each dictionary has keys for text and color.
You can use a trick on the array to get all the values in one:
First, your code to extract the JSON into an NSArray:
NSString *jsonPath = [[NSBundle mainBundle] pathForResource:#"notes"
ofType:#"json"];
NSError *e = nil;
NSData *data = [[NSData alloc] initWithContentsOfFile:jsonPath];
NSArray *parsed = [NSJSONSerialization JSONObjectWithData:data
options:NSJSONReadingMutableContainers
error:&e];
Now the trick:
NSArray *textEntries = [parsed valueForKey: #"text"];
NSArray *colorEntries = [parsed valueForKey: #"color"];
EDIT:
The trick is in sending the valueForKey message to an array. When you do that, it passes on the message to every object in the array. The array then builds a new array with the answer it gets back from each object it contains and returns the resulting array to you. This does a whole lot of work for you with a very simple statement.

Related

How to retrieve data from local file of json to a dictionary in Objective C iOS

I have trouble in retrieving the data from my JSON file to a dictionary and then I will access the values inside array of that dictionary to take the time and compare the time what I have done so far is that.
Note: I have multiple timings for one month.
in my viewDidLoad I have defined
- (void)viewDidLoad {
[super viewDidLoad];
NSURL *url = [NSURL fileURLWithPath:#"/Users/macbook/Desktop/Test/Test/myFile.json"];
NSString *fileContent = [NSString stringWithContentsOfURL:url encoding:NSUTF8StringEncoding error:nil];
NSLog(#"Json data is here %#", fileContent);
saving data in dictionary
NSArray *data = [[theFeedString JSONValue] objectForKey:#"data"];
for (NSDictionray *dict in data) {
NSString *timings = [[dict objectForKey:#"timings"] intValue];
}
in my console I get all the data from my json and my json look like this
{
"data": [
{
"timings": {
"Sunrise": "07:14 (PKT)",
"Sunset": "18:15 (PKT)",
"Midnight": "00:45 (PKT)"
}
},
{
"timings": {
"Sunrise": "07:13 (PKT)",
"Sunset": "06:40 (PKT)",
"Midnight": "00:45 (PKT)"
}
}
]
}
You should do like this way, where Palettes.json is a local file.
NSString *filePath = [[NSBundle mainBundle] pathForResource:#"Palettes" ofType:#"json"];
NSData *data = [NSData dataWithContentsOfFile:filePath];
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:nil];
Let me know if there is any query.
UPDATE
According to your Output of JSON, you will get data array like this,
NSArray *data = json["data"];
[data enumerateObjectsUsingBlock:^(id object, NSUInteger idx, BOOL *stop) {
NSDictionary *timings = object["timings"];
NSString *sunrise = timings["Sunrise"];
}];
You can iterate through data array to get timings

How to parse a JSON dictionary and put the keys and values in separate arrays - Objective C

I'm trying to parse www.fixer.io JSON to get currency data. I've been having trouble parsing the JSON and trying to separate the keys and values from the "rates" dictionary. I need them separate so I can put them in arrays to display the currency name (ex: USD, EUR, JPN) and their respective rates.
I've read that I have to use the "allKeys" and "allValues" to do this but so far I'm having no luck. Any ideas?
NSURL *fixerURL = [NSURL URLWithString:#"http://api.fixer.io/latest?base=USD"];
NSData *data = [NSData dataWithContentsOfURL:fixerURL];
NSError *error;
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&error];
NSMutableArray *arr = [[NSMutableArray alloc]init];
NSMutableArray *arr2 = [[NSMutableArray alloc]init];
NSArray *names;
NSArray *rates;
for (names in json) {
names = [json allKeys];
for (rates in json) {
rates = [json allValues];
}
[arr addObject:names];
[arr2 addObject:rates];
}
self.currencyList = arr;
self.currencyRates = arr2;
[self updateTableView];
Here is the JSON ---> http://api.fixer.io/latest?base=USD
Hope this will help you,
NSURL *fixerURL = [NSURL URLWithString:#"http://api.fixer.io/latest?base=USD"];
NSData *data1 = [NSData dataWithContentsOfURL:fixerURL];
NSError *error;
NSDictionary *json1 = [NSJSONSerialization JSONObjectWithData:data1 options:kNilOptions error:&error];
NSLog(#"%#",json1);
NSDictionary *json = [[NSDictionary alloc]initWithDictionary:[json1 objectForKey:#"rates"]];
NSMutableArray *arr = [[NSMutableArray alloc] initWithArray:[json allKeys]];
NSMutableArray *arr2 = [[NSMutableArray alloc]initWithArray:[json allValues]];
NSLog(#"%#",arr);
NSLog(#"%#",arr2);
as the rates key contains a dictionary not an array so we can’t get country name and currency as dictionary format
if you want to get the country name and currency in different array so you need to get them separately like bellow
NSArray *arrKeys = [[json valueForKey:#"rates"] allKeys];
NSArray *arrValues = [[json valueForKey:#"rates"] allValues];
Based on your JSON response you have to get yoiur all currency rate as below
NSMutableArray *allCurrencyKey = [[json valuesForKey:#"rates"] allKeys];
NSMutableArray *allRates = [json valueForKey:#"rates"];
for(NSString *strCurKey in allCurrencyKey)
{
NSLog (#" %# rate is %# ", strCurKey, [allRates valueForKey :strCurKey ]);
}
Hope this will helps you.
I'm not sure what error you're getting, but when I try to run this code I get data coming back as nil. Which of course crashes the app.
It probably has something to do with the method you are using to fetch the JSON.
dataWithContentsOfURL: should not be used for network-based URLs.
dataWithContentsOfURL:
To fetch data over the network, take a look at NSURLSession.
Use below code to get Rates Nad Currency Names
NSDictionary *json = [NSJSONSerialization JSONObjectWithData:data options:kNilOptions error:&error];
By this response you can get all rates:
NSMutableDictionary *rates = [json objectForKey:#"rates"];
//Get All Currency Names by `allKeys`.
NSArray *currencyTitles = [rates allKeys];
for(NSString *currencyName in currencyTitles){
//Get Value.
NSString *aStrCurValue = [rates objectForKey:currencyName];
}

How to parse such a json array?

Im having hard time while trying to parse the following json array. How to parse it. The other answers in web doesn't seem to solve my problem.
{
"status": 1,
"value": {
"details": [
{
"shipment_ref_no": "32",
"point_of_contact": {
"empid": ""
},
"products": {
"0": " Pizza"
},"status": "2"
},
{
"shipment_ref_no": "VAPL/EXP/46/14-15",
"point_of_contact": {
"empid": "60162000009888"
},
"products": {
"0": "MAIZE/CORN STARCH"
},
"status": "5"
}
]
}
}
I have to access the values of each of those keys.
Following is my code
NSString* pendingResponse = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
NSData *jsonData = [pendingResponse dataUsingEncoding:NSUTF8StringEncoding];
NSDictionary *jsonDic = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingAllowFragments error:nil];
NSArray *argsArray = [[NSArray alloc] initWithArray:[jsonDic objectForKey:#"details"]];
NSDictionary *argsDict = [[NSDictionary alloc] initWithDictionary:[argsArray objectAtIndex:0]];
NSLog(#"keys = %#", jsonDic[#"values"]);
This is how you can parse your whole dictionary:
NSDictionary *dataDictionary = [NSJSONSerialization JSONObjectWithData:data options:0 error:nil];
NSArray *details = [[dataDictionary objectForKey:#"value"] objectForKey:#"details"];
for (NSDictionary *dic in details) {
NSString *shipmentRefNo = dic[#"shipment_ref_no"];
NSDictionary *pointOfContact = dic[#"point_of_contact"];
NSString *empId = pointOfContact[#"empid"];
NSDictionary *products = dic[#"products"];
NSString *zero = products[#"0"];
NSString *status = dic[#"status"];
}
NSString *pendingResponse = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
NSData *jsonData = [pendingResponse dataUsingEncoding:NSUTF8StringEncoding];
NSDictionary *jsonDic = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingAllowFragments error:nil];
NSArray *argsArray = [[NSArray alloc] initWithArray:[jsonDic objectForKey:#"details"]];
//argsArray holds objects in form of NSDictionary.
for(NSDictionary *response in argsArray) {
//String object
NSLog(#"%#", [response valueForKey:#"shipment_ref_no"]);
//Dictionary object
NSLog(#"%#", [[response objectForKey:#"point_of_contact"] valueForKey:#"empid"]);
//String object
NSLog(#"%#", [response valueForKey:#"status"]);
//Dictionary object
NSLog(#"%#", [[response objectForKey:#"products"] valueForKey:#"0"]);
}
I believe you should surely ask your server developer to update the response format.
Also, you can always use Model classes to parse your data. Please check this, How to convert NSDictionary to custom object.
And yes, I'm using this site to check my json response.
EDIT: Following answer is in javascript!
You can parse your json data with:
var array = JSON.parse(data);
and then you can get everything like this:
var refno = array["value"]["details"][0]["shipment_ref_no"];
you can parse like ...
NSDictionary *jsonDic = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingAllowFragments error:nil];
NSDictionary *dictValue = [[NSDictionary alloc] initWithDictionary:[jsonDic objectForKey:#"value"]];
NSArray *arrDetails = [[NSArray alloc] initWithArray:[dictValue objectForKey:#"details"]];
for (int i=0; i<arrDetails.count; i++)
{
NSDictionary *dictDetails=[arrDetails objectAtIndex:i];
NSDictionary *dictContact = [[NSDictionary alloc] initWithDictionary:[dictDetails objectForKey:#"point_of_contact"]];
NSDictionary *dictProduct = [[NSDictionary alloc] initWithDictionary:[dictDetails objectForKey:#"products"]];
}
NSDictionary *response = //Your json
NSArray *details = response[#"value"][#"details"]
etc. Pretty easy
Update your code as follows. You are trying to read the details array from the top level whereas in your data its inside the value key. So you should read the value dict and within that read the details array.
NSString* pendingResponse = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
NSData *jsonData = [pendingResponse dataUsingEncoding:NSUTF8StringEncoding];
NSDictionary *jsonDic = [NSJSONSerialization JSONObjectWithData:jsonData options:NSJSONReadingAllowFragments error:nil];
NSDictionary *valueDict = [jsonDic objectForKey:#"value"];
NSArray *argsArray = [[NSArray alloc] initWithArray:[valueDict objectForKey:#"details"]];
NSDictionary *argsDict = [[NSDictionary alloc] initWithDictionary:[argsArray objectAtIndex:0]];
NSLog(#"keys = %#", jsonDic[#"values"]);
I think your problem is that you have:
NSLog(#"keys = %#", jsonDic[#"values"]);
But it should be:
NSLog(#"keys = %#", jsonDic[#"value"]);
Below is code for parsing JSON array. i have used to parse JSON array from file but you can also do this using response link also.I have provided code for both and are below.
// using file
NSString *str = [[NSBundle mainBundle] pathForResource:#"test" ofType:#"json"];
NSData *data = [[NSData alloc]initWithContentsOfFile:str];
NSMutableDictionary *dict = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
NSMutableDictionary *dictValues = [[NSMutableDictionary alloc]initWithDictionary:[dict valueForKey:#"value"]];
NSMutableArray *array = [[NSMutableArray alloc]initWithArray:[dictValues valueForKey:#"details"] copyItems:YES];
NSLog(#"Array Details :- %#",array);
// using url
NSURL *url = [NSURL URLWithString:#"www.xyz.com"]; // your url
NSData *data = [[NSData alloc]initWithContentsOfURL:url];
NSMutableDictionary *dict = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingMutableContainers error:nil];
NSMutableDictionary *dictValues = [[NSMutableDictionary alloc]initWithDictionary:[dict valueForKey:#"value"]];
NSMutableArray *array = [[NSMutableArray alloc]initWithArray:[dictValues valueForKey:#"details"] copyItems:YES];
NSLog(#"Array Details :- %#",array);

IOS/xcode debug crash handling json feed

IOS newb here having trouble with debugging.
Am trying to handle a json feed but code below is breaking at
- (void)viewDidLoad {
[super viewDidLoad];
shnote = #"shnote”;
lnote = #"lnote”;
myObject = [[NSMutableArray alloc] init];
self.title=#"Challenges";
NSData *jsonSource = [NSData dataWithContentsOfURL:
[NSURL URLWithString:#"http://www.~~/webservice.php"]];
id jsonObjects = [NSJSONSerialization JSONObjectWithData:
jsonSource options:NSJSONReadingMutableContainers error:nil];
for (NSDictionary *dataDict in jsonObjects) {
//BREAKS HERE
NSString *shnote_data = [dataDict objectForKey:#"shnote”];
//ABOVE LINE HIGHLIGHTED IN GREEN AT BREAKPOINT
NSString *lnote_data = [dataDict objectForKey:#"lnote”];
dictionary = [NSDictionary dictionaryWithObjectsAndKeys:
shnote_data, shnote,lnote_data, lnote,nil];
[myObject addObject:dictionary];
}
/*
*/
}
The line highlighted in console is
dataDict = (NSDictionary *const)#"notes"
notes is name of table but other than that I am clueless.
Would appreciate any suggestions.
Your data source is of the format:
{
"notes": [
{
"row": {
"shnote": <...>,
"lnote": <...>
}
},
{
"row": {
"shnote": <...>,
"lnote": <...>
}
},
<...>
]
}
Steps to fetch each row content should therefore be:
Read value of notes property
Iterate through each row
Read value of row property
Read shnote and lnote properties
You're missing steps 1, 2 and 3. In code:
NSURL *url = [NSURL URLWithString:#"http://www.~~/webservice.php"];
NSData *jsonSource = [NSData dataWithContentsOfURL:url];
NSDictionary *jsonObject = [NSJSONSerialization JSONObjectWithData:jsonSource options:NSJSONReadingMutableContainers error:nil];
NSDictionary *notes = jsonObject[#"notes"];
for(NSDictionary *note in notes) {
NSDictionary *row = note[#"row"];
NSString *shnote = row[#"shnote"];
NSString *lnote = row[#"lnote"];
NSLog(#"%#, %#", shnote, lnote);
}

Using NSArray and NSDictionary to access a JSON object without a root element

Here's an example of my data:
[
{
code: "DRK",
exchange: "BTC",
last_price: "0.01790000",
yesterday_price: "0.01625007",
top_bid: "0.01790000",
top_ask: "0.01833999"
}
]
I'm trying to retrieve the value for last_price by loading the contents of my NSDictionary into an Array.
NSURL *darkURL = [NSURL URLWithString:#"https://api.mintpal.com/v1/market/stats/DRK/BTC"];
NSData *darkData = [NSData dataWithContentsOfURL:darkURL];
NSError *error = nil;
NSDictionary *darkDict = [NSJSONSerialization JSONObjectWithData:darkData options:0 error:&error];
self.darkPosts = [NSMutableArray array];
NSArray *darkPostArray = [darkDict objectForKey:#""];
for (NSDictionary *darkDict in darkPostArray) {...
But my json doesn't have a root element, so what do I do?
Additionally, when using the suggested answer, the output is ("...
- (void)viewDidLoad{
[super viewDidLoad];
NSURL *darkURL = [NSURL URLWithString:#"https://api.mintpal.com/v1/market/stats/DRK/BTC"];
NSData *darkData = [NSData dataWithContentsOfURL:darkURL];
NSError *error = nil;
NSDictionary *darkDict = [NSJSONSerialization JSONObjectWithData:darkData options:0 error:&error];
NSString *lastP = [darkDict valueForKey:#"last_price"];
self.dark_label.text = [NSString stringWithFormat: #"%#", lastP];
}
It looks like you are wanting to iterate over your results. The root element is an array not a dictionary so you can just start iterating
NSError *error = nil;
NSArray *items = [NSJSONSerialization JSONObjectWithData:darkData
options:kNilOptions
error:&error];
if (!items) {
NSLog(#"JSONSerialization error %#", error.localizedDescription);
}
for (NSDictionary *item in items) {
NSLog(#"last_price => %#", item[#"last_price"]);
}
If you literally just want to collect an array of the last_price's then you can so this
NSArray *lastPrices = [items valueForKey:#"last_price"];
Convert the JSON to an NSArray with NSJSONSerialization. Then access the value:
NSData *darkData = [#"[{\"code\":\"DRK\",\"exchange\": \"BTC\",\"last_price\": \"0.01790000\",\"yesterday_price\": \"0.01625007\",\"top_bid\": \"0.01790000\"}, {\"top_ask\": \"0.01833999\"}]" dataUsingEncoding:NSUTF8StringEncoding];
NSArray *array = [NSJSONSerialization JSONObjectWithData:darkData
options:0
error:&error];
NSString *value = array[0][#"last_price"];
NSLog(#"value: %#", value);
NSLog output:
value: 0.01790000
If you are having trouble post the code you have written to get some help.
-- updated for new OP code:
The web service returns a JSON array or dictionaries not a JSON dictionary. First you have to index into the array and then index into the dictionary.
NSURL *darkURL = [NSURL URLWithString:#"https://api.mintpal.com/v1/market/stats/DRK/BTC"];
NSData *darkData = [NSData dataWithContentsOfURL:darkURL];
NSError *error = nil;
NSArray *darkArray = [NSJSONSerialization JSONObjectWithData:darkData options:0 error:&error];
NSDictionary *darkDict = darkArray[0];
NSString *lastP = [darkDict valueForKey:#"last_price"];
NSLog(#"lastP: %#", lastP);
NSLog output:
lastP: 0.01970000
Note that the two lines:
NSDictionary *darkDict = darkArray[0];
NSString *lastP = [darkDict valueForKey:#"last_price"];
can be replaced with the single line using array indexing:
NSString *lastP = darkArray[0][#"last_price"];
Where the "[0]" gets the first array element which is a NSDictionary and the "[#"last_price"]" gets the names item from the dictionary.

Resources