working with NSMutableArray data handeling [closed] - iphone

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 9 years ago.
Improve this question
I have 2 classes:
MainVC
DownloadedFilesView
In MainVC class I have a NSMutableArray which stores list of all files of iPhone Directory. This array is datasource for my tableview (present in DownloadedFilesView). Upon selecting particular row (from MainVC tableview), I'm sending this data from MainVC to DownloadedFilesView like this:
if (indexPath.section == 1) {
DownloadedFilesView *downloadView = [[DownloadedFilesView alloc] initWithNibName:#"DownloadedFilesView" bundle:nil];
int count;
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *path = [paths objectAtIndex:0];
NSArray *directoryContent = [[NSFileManager defaultManager] contentsOfDirectoryAtPath:path error:NULL];
for (count = 0; count < (int)[directoryContent count]; count++)
{
NSString *fileNames = [directoryContent objectAtIndex:count];
[downloadView.arrayOfDirFiles addObject:fileNames];
}
[self.navigationController pushViewController:downloadView animated:YES];
}
and I'm saving this datasource into another array "arrayOfDirFiles" (which is in DownloadedFilesView). Now I'm initializing this array in
initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
like:
arrayOfDirFiles = [[NSMutableArray alloc] init];
Now this array is datasource for my tableview in DownloadedFilesView
tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{
if (theTableView.editing) {
//arrayOfFileNamesToSave is the array which I want filtered when selecting particular cell
[arrayOfFileNamesToSave addObject:[arrayOfDirFiles objectAtIndex:indexPath.row]];
}
//NSLog(#"aaa....%#",arrayOfFileNamesToSave);
}
Now this is throwing an error. What is the best way to make this working? Please help!
Thanks in advance!

I think the best way is to pass the whole directoryContent array to downloadView.
downloadView.arrayOfDirFiles = directoryContent
Please ensure that arrayOfDirFiles is defined as strong/retain in DownloadedFilesView.

Related

NSMutableArray Not Retaining Objects Outside Method [closed]

This question is unlikely to help any future visitors; it is only relevant to a small geographic area, a specific moment in time, or an extraordinarily narrow situation that is not generally applicable to the worldwide audience of the internet. For help making this question more broadly applicable, visit the help center.
Closed 9 years ago.
In my -viewDidLoad method, I initialize many NSMutableDictionaries, and add them to an initialized NSMutableArray declared via #property in the class header file. The relevant code is shown below. In short, I'm webscraping information from an HTML webpage.
NSMutableDictionary *dict = [[NSMutableDictionary alloc] init];
_regionalDicts = [[NSMutableArray alloc] init];
for (int i = 0; i < [strings count]; i++) {
NSString *str = [strings objectAtIndex:i];
//Property parser:
if ([str rangeOfString:#"<td>"].location != NSNotFound) {
NSString *parsedTD1 = [str stringByReplacingOccurrencesOfString:#"<td>" withString:#""];
NSString *parsedTD2 = [parsedTD1 stringByReplacingOccurrencesOfString:#"</td>" withString:#""];
NSString *parsedTD3 = [parsedTD2 stringByReplacingOccurrencesOfString:#" " withString:#"\n"];
NSString *final = [parsedTD3 stringByReplacingOccurrencesOfString:#"\t" withString:#""];
//NSLog(#"Final string: %#", final);
if ([final isEqualToString:#""]) {
continue;
}
if (gotEventType == NO) {
gotEventType = YES;
[dict setObject:final forKey:#"type"];
continue;
}
if (gotRegional == YES && gotLocation == NO) {
gotLocation = YES;
[dict setObject:final forKey:#"location"];
continue;
}
if (gotLocation == YES && gotCity == NO) {
gotCity = YES;
NSString *cityToReturn = [final stringByReplacingOccurrencesOfString:#"\n" withString:#""];
[dict setObject:cityToReturn forKey:#"city"];
continue;
}
if (gotRegional == YES && gotEventType == YES && gotCity == YES && gotLocation == YES && gotURL == YES) {
gotRegional = NO;
gotEventType = NO;
gotCity = NO;
gotLocation = NO;
gotURL = NO;
NSLog(#"Regional: %#", [dict objectForKey:#"regional"]);
NSLog(#"Type: %#", [dict objectForKey:#"type"]);
NSLog(#"City: %#", [dict objectForKey:#"city"]);
//Testing to see if anything is nil
NSLog(#"Location: %#\n", [dict objectForKey:#"location"]);
if (!_regionalDicts) {
NSLog(#"Dict is nil");
}
[_regionalDicts addObject:dict];
NSLog(#"Objects in array: %u", [_regionalDicts count]);
NSMutableDictionary *tempDict = [_regionalDicts objectAtIndex:[_regionalDicts count]-1];
NSLog(#"Regional in array: %#", [tempDict objectForKey:#"regional"]);
[dict removeAllObjects];
continue;
}
It's clear that the generated dictionaries are generated and retained within the _regionalDicts mutable array, which is declared in the header file like this:
#property (strong, nonatomic) IBOutlet NSMutableArray *regionalDicts;
However, when I attempt to pass in information to table view cells in in the same class, the dictionaries' contents are null. There are as many objects within the array as dictionaries I am expecting, but they do not contain any content.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
}
if (_regionalDicts) {
NSMutableDictionary *dict = [_regionalDicts objectAtIndex:0];
NSLog(#"Setting label %#", [dict objectForKey:#"city"]);
[cell.textLabel setText:[dict objectForKey:#"regional"]];
}
return cell;
}
Returns:
2013-04-01 19:58:50.250 MatchScrape[53570:207] Setting label (null)
I can only imagine that a memory management issue is to blame. Why would the contents of a class array be nullified when accessed outside the scope of the method they are added in, but allow the array to retain the same count?
You seem to believe that adding the dictionary to the array doesn't actually add the dictionary to the array, but instead adds a copy of the dictionary. You're probably thinking of how it might work in a language like C++ — but that isn't how it works here. Remember, Objective-C objects are always accessed by reference: you never directly store the object itself in a variable or array — you're just shuffling around a pointer to the actual object, which usually lives on the heap.
So when you add _dict to the array, the one in the array is the very same object referenced by _dict. Anything you do to that dictionary — no matter what reference you use — will be reflected everywhere else that dictionary is referenced, because it's the same dictionary. You haven't made a copy of it. Thus, when you do [_dict removeAllObjects], that removes all the objects from the dictionary and you end up with an array that contains the same empty dictionary a bunch of times.

iPhone sdk how to receive string value?

In my application, i need to provide three languages support. My default language will be English. Once the user selects other language in setting controller the entire application should change into that particular language. For this i decided to have a plist file with all the three languages and their data in it.Now my default language is English that is fine. Now i changed the language using plist in LanguageController and pushed to home controller. The selected language(French) string was not received in my home controller. Here is my code,
//LanguageController.h
NSMutableDictionary *allDictElements;
NSString *selectedLanguage1;
NSArray *dummy;
#property(nonatomic,retain) NSMutableDictionary *allDictElements;
#property(nonatomic,retain) NSString *selectedLanguage1;
#property(nonatomic,retain) NSArray *dummy;
//LanguageController.m
#synthesize allDictElements,selectedLanguage1,dummy;
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
NSString *path= [[NSBundle mainBundle] pathForResource:#"Language" ofType:#"plist"];
allDictElements = [[NSMutableDictionary alloc] initWithContentsOfFile:path];
NSLog(#"%#allDictElements",allDictElements);
LeeValleyHomeViewController *homeController = [[LeeValleyHomeViewController alloc] initWithNibName:#"LeeValleyHomeViewController" bundle:[NSBundle mainBundle]];
if (indexPath.row ==0)
{
//bookshelf button
NSMutableDictionary *english=[[NSMutableDictionary alloc]init];
english=[allDictElements objectForKey:#"English Language"];
dummy=[english objectForKey:#"English"];
selectedLanguage1=[dummy objectAtIndex:0];
NSLog(#"english bookshelf button:%#",selectedLanguage1);
homeController.selectedLanguage = selectedLanguage1;
NSLog(#"sel lang:%#",homeController.selectedLanguage);
} else if (indexPath.row ==1) {
//bookshelf button
NSMutableDictionary *french=[[NSMutableDictionary alloc]init];
french=[allDictElements objectForKey:#"French Language"];
dummy=[french objectForKey:#"French"];
selectedLanguage1=[dummy objectAtIndex:0];
NSLog(#"french bookshelf button:%#",selectedLanguage1);
homeController.selectedLanguage = selectedLanguage1;
NSLog(#"sel lang:%#",homeController.selectedLanguage);
} else {
NSMutableDictionary *spanish=[[NSMutableDictionary alloc]init];
spanish=[allDictElements objectForKey:#"Spanish Language"];
dummy=[spanish objectForKey:#"Spanish"];
selectedLanguage1=[dummy objectAtIndex:0];
NSLog(#"spanish bookshelf button:%#",selectedLanguage1);
homeController.selectedLanguage = selectedLanguage1;
NSLog(#"sel lang:%#",homeController.selectedLanguage);
}
[self.navigationController pushViewController:homeController animated:YES];
}
Here in this controller am receiving the selected language string finely.
//LeeValleyHomeViewController.h
NSString *selectedLanguage;
#property (nonatomic,retain) NSString *selectedLanguage;
//LeeValleyHomeViewController.m
#synthesize selectedLanguage;
- (void)viewDidLoad
{
LanguageViewController lvc = [LanguageViewController alloc]init];
bookshelfbtn.titleLabel.text = lvc.selectedLanguage1;
NSLog(#"button title:%#",bookshelfbtn.titleLabel.text);
//bookshelfbtn.titleLabel.text = selectedLanguage;
}
Here in this controller am not receiving that string value. What's wrong with my code? or how can i do this? Thanks in advance.
You can save the selected language in NSUserDefaults and retrieve it in ViewDidLoad of LeeValleyHomeViewController.m like this.....
In your,
(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
// after selecting language
[[NSUserDefaults standardUserDefaults]setValue:selectedLanguage1 forKey:#"language"];
[[NSUserDefaults standardUserDefaults]synchronize];
}
//LeeValleyHomeViewController.m
(void)viewDidLoad
{
NSLog(#"button title:%#",bookshelfbtn.titleLabel.text);
bookshelfbtn.titleLabel.text = [[NSUserDefaults standardUserDefaults]valueForKey forKey:#"language"];
}
I'm not certain if "LanguageController" you have in the first block of code is the same thing as "LanguageViewController" in your second block of code.
But if it is, why do you think the "selectedLanguage1" property would be set to anything other than zero after you instantiate that "LanguageViewController"? The user hasn't touched any cell yet so the only language that it could possibly be is English (with a value of value zero).

How to reverse the data in NSMutableArray? [duplicate]

This question already has answers here:
Closed 11 years ago.
Possible Duplicate:
How to display an array in reverse order in objective C
I have an NSMutableArray and this array contains information nicely in UITableView.
but I want to display latest information first in UITableView. Right now the earliest information comes first in UITableView. My code is as follows:
NSMutableArray *entries = [NSMutableArray array];
[self parseFeed:doc.rootElement entries:entries];
for (RSSEntry *entry in entries) {
[allEntries insertObject:entry atIndex:0]; //insertIdx];
[self.tableView insertRowsAtIndexPaths:[NSArray arrayWithObject:[NSIndexPath indexPathForRow:0 inSection:0]] withRowAnimation:UITableViewRowAnimationRight];
}
then How can I reverse the information in NSMutableArray?
How about just enumerating the contents of entries in reverse order?
for (RSSEntry *entry in [entries reverseObjectEnumerator]) {
...
}
If you just want to take an array and create a reversed array, you can do this:
NSArray *reversedEntries = [[entries reverseObjectEnumerator] allObjects];
You can try like this way:
for (int k = [originalArray count] - 1; k >= 0; k--) {
[reverseArray addObject:[originalArray objectAtIndex:k]];
}

How to implement UITableView search functionality

My iPhone application has a UITable View implemented with search functionality in it. The values in the table are grouped into sections from A-Z. Whenever a user tap on particular cell in the table it loads a detail view controller which gives all the values of that particular user. Now my problem is whenever I search some contact and tap on a particular user to check his detail view it always returns a contact starting with letter A. So, my doubt is how to implement this search functionality. Is there a way to get the name of the contact I tapped..Please check this screenshot.. For example if I search some contact starting with letter 'B' and tap on that contact it loads the detail view of a contact starting with letter 'A'. I get all the values from the database. Can you please help me out...
This is the code:
The code I wrote here is in a method:
I am getting all the contacts from database and assigning to an array contacts. Then I am grouping all the contacts according to the alphabets and grouping everything into a dictionary with keys as A-Z and values as name of contacts starting with these letters. Now when I search for a particular contact his name may start with either A ,B or Z..so in the search bar when I search for a particular contact for example a contact starting with letter Z, in this case it gives the details of a person with A. I want this to change so that whenever I tap on a particular contact it should load its details. I am unable to figure out how to do it..
contacts = [[db getContacts:#"Contacts"] componentsSeparatedByString:#","];
[db cleanup];
NSMutableArray *tempArray = [[NSMutableArray alloc] init];
NSString *charString;
for (int i=65; i<91; i++) {
charString = [NSString stringWithFormat:#"%c",(char *)i];
[tempArray addObject:charString];
}
[charString release];
NSMutableDictionary *dict = [[NSMutableDictionary alloc] init];
for (int i=0; i<[tempArray count]; i++) {
NSMutableArray *contactsByIndex = [[[NSMutableArray alloc] init]autorelease];
NSString *tempChar = [tempArray objectAtIndex:i];
for (int j=0; j<[contacts count]-1; j++)
{
NSString *test = [contacts objectAtIndex:j];
NSString *tempString = [test substringToIndex:1];
if ([tempString isEqualToString:tempChar]) {
[contactsByIndex addObject:[contacts objectAtIndex:j]];
}
}
[dict setObject:contactsByIndex forKey:[tempArray objectAtIndex:i]];
}
self.contactNames = dict;
NSArray *array = [[contactNames allKeys] sortedArrayUsingSelector:#selector(caseInsensitiveCompare:)];
self.contactKeys = array;
[dict release];
[tempArray release];
//---display the searchbar---
self.tableView.tableHeaderView = searchBar;
searchBar.autocorrectionType = UITextAutocorrectionTypeYes;
listOfContacts = [[NSMutableArray alloc] init];
for (NSString *key in array)
{
NSArray *contactsArray = [contactNames objectForKey:key];
for (NSString *name in contactsArray) {
[listOfContacts addObject:name];
}
}
- (void) searchContactsTableView {
//---clears the search result---
[searchResult removeAllObjects];
for (NSString *str in listOfContacts) {
NSRange titleResultsRange = [str rangeOfString:searchBar.text options:NSCaseInsensitiveSearch];
if (titleResultsRange.length > 0)
[searchResult addObject:str];
}
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
// Navigation logic may go here. Create and push another view controller.
NSString *selectedRow=nil;
if (isSearchOn) {
selectedRow=[searchResult objectAtIndex:indexPath.row];
}
DetailViewController *detailViewController;
int section_index=[indexPath indexAtPosition:[indexPath length]-2];
int sugarid_Index = [indexPath indexAtPosition: [indexPath length]-1];
NSString* sectionName=[contactKeys objectAtIndex:section_index];
NSLog(#"%#",sectionName);
//This is a method which gets the details of a particular contact based on the section and the row selected..Contacts is the table name
NSString *getContact=[db getId:#"Contacts" bySection:sectionName andIndex:sugarid_Index];
id=[db getContact:#"Contacts" id:getContact];
// Pass the selected object to the new view controller.
detailViewController = [[DetailViewController alloc] initWithNibName:#"DetailViewController" bundle:nil];
detailViewController.eachContact=contactForSugarId;
[self.navigationController pushViewController:detailViewController animated:YES];
}
When I search for a contact it should search for the name in database and should return its details. Is there a way to do it..please let me know or is there a way to get the name of the cell i.e. the contact name so that I can use that in one of my database methods to retrieve the details of the contact I selected.
Off hand it sounds like you're looking in the wrong array of contacts after the search. You need to have two arrays. One with all the contacts, and one with the filtered contacts. When you search, put all the results in order in the filtered list, and pull the details from that one.
Does this make sense?
If not, try posting a bit of code, and explaining your structure.

Adding # & search sign to TableIndex in UITableView

In iPhone native Phone book - there is a search character at the top & # character at the bottom.
I want to add both of that character in my table Index.
Currently I have implemented following code.
atoz=[[NSMutableArray alloc] init];
for(int i=0;i<26;i++){
[atoz addObject:[NSString stringWithFormat:#"%c",i+65]];
}
- (NSArray *)sectionIndexTitlesForTableView:(UITableView *)tableView{
return atoz;
}
How to have # character & search symbol in my UITableView?
The best way to tackle this is to make use of the tools the framework provides. In this case, you want to use UILocalizedIndexedCollation (developer link).
I also have a decorator for this class that is designed to insert the {{search}} icon for you and handle the offsets. It is a like-for-like drop-in replacement for UILocalizedIndexedCollation.
I've posted a more in-depth description of how to use this on my blog. The decorator is available here (Gist).
The basic idea is to group your collection into an array of arrays, with each array representing a section. You can use UILocalizedIndexedCollation (or my replacement) to do this. Here's a small NSArray category method I use to do this:
#implementation NSArray (Indexing)
- (NSArray *)indexUsingCollation:(UILocalizedIndexedCollation *)collation withSelector:(SEL)selector;
{
NSMutableArray *indexedCollection;
NSInteger index, sectionTitlesCount = [[collation sectionTitles] count];
indexedCollection = [[NSMutableArray alloc] initWithCapacity:sectionTitlesCount];
for (index = 0; index < sectionTitlesCount; index++) {
NSMutableArray *array = [[NSMutableArray alloc] init];
[indexedCollection addObject:array];
[array release];
}
// Segregate the data into the appropriate section
for (id object in self) {
NSInteger sectionNumber = [collation sectionForObject:object collationStringSelector:selector];
[[indexedCollection objectAtIndex:sectionNumber] addObject:object];
}
// Now that all the data's in place, each section array needs to be sorted.
for (index = 0; index < sectionTitlesCount; index++) {
NSMutableArray *arrayForSection = [indexedCollection objectAtIndex:index];
NSArray *sortedArray = [collation sortedArrayFromArray:arrayForSection collationStringSelector:selector];
[indexedCollection replaceObjectAtIndex:index withObject:sortedArray];
}
NSArray *immutableCollection = [indexedCollection copy];
[indexedCollection release];
return [immutableCollection autorelease];
}
#end
So, given an array of objects, for example books that I want to divide into sections based on their name (the Book class has a name method), I would do this:
NSArray *books = [self getBooks]; // etc...
UILocalizedIndexedCollation *collation = [UILocalizedIndexedCollation currentCollation];
NSArray *indexedBooks = [books indexUsingCollation:collation withSelector:#selector(name)];