У меня есть приложение для книг с UISearchBar, где пользователь вводит любое имя книги и получает результаты поиска (из вызова ext API) ниже по мере ввода.
В моем приложении используется переменная-одиночка, которая называетсяretrievedArray, в котором хранятся все книги.
@interface Shared : NSObject {
NSMutableArray *books;
}
@property (nonatomic, retain) NSMutableArray *books;
+ (id)sharedManager;
@end
Доступ к нему осуществляется в нескольких файлах .m с использованием NSMutableArray * retrievedArray;... в заголовочном файле
retrievedArray = [[Shared sharedManager] books];
Мой вопрос заключается в том, как обеспечить, чтобы значения внутри retrievedArray оставались синхронизированными по всем классам.
Фактически значения внутри retrievedArray добавляются черезNSXMLParser (т.е. через API внешнего веб-сервиса).Существует отдельный файл XMLParser.m, где я делаю весь анализ и заполняю массив.Синтаксический анализ выполняется в отдельном потоке.
- (void) run: (id) param {
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSXMLParser *parser = [[NSXMLParser alloc] initWithContentsOfURL: [self URL]];
[parser setDelegate: self];
[parser parse];
[parser release];
NSString *tmpURLStr = [[self URL]absoluteString];
NSRange range_srch_book = [tmpURLStr rangeOfString:@"v1/books"];
if (range_srch_book.location != NSNotFound)
[delegate performSelectorOnMainThread:@selector(parseDidComplete_srch_book) withObject:nil waitUntilDone:YES];
[pool release];
}
- (void) parseXMLFile: (NSURL *) url
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
[self setURL: url];
NSThread* myThread = [[NSThread alloc] initWithTarget:self
selector:@selector(run:)
object: nil];
[retrievedArray removeAllObjects];
[myThread start];
[pool release];
}
Кажется, что есть некоторые проблемы с синхронизацией, если пользователь печатает очень быстро (кажется, работает нормально, если пользователь печатает медленно) .... Так что2 вида, в которых отображается содержимое объекта в этом элементе общего массива;Список и детали.Если пользователь быстро набирает и нажимает A в представлении «Список», он отображается в виде «B». Это основная проблема.
Я буквально попробовал все решения, которые мог придумать, но до сих пор не могучтобы исправить проблему.
ПРИМ. РЕДАКТИРОВАНИЯ ВЫПУСКА СИНХРОНИЗАЦИИ: В представлении списка, если отображаются 3 элемента, скажем Item1, Item2 и Item3, и если пользователь нажимает на Item2, он отображается Item3 в подробном представлении (то есть, если не сказатьправильные данные)
Ниже приведен код, который выполняется при нажатии элемента в представлении списка;
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
// Navigation logic -- create and push a new view controller
if(bookdetailCustom == nil)
bookdetailCustom = [[BookDetailCustom alloc] initWithNibName:@"BookDetailCustom" bundle:[NSBundle mainBundle]];
//aBook = [retrievedArray objectAtIndex:indexPath.row];
bookdetailCustom.selectedIndex = indexPath.row;
[self.navigationController pushViewController:bookdetailCustom animated:YES];
[bookdetailCustom release];
bookdetailCustom = nil;
}
Вот как выглядит searchTabkleView
- (void) searchTableView {
NSString *searchText = searchBar.text;
NSMutableArray *searchArray = [[NSMutableArray alloc] init];
for (int i=0;i<[retrievedArray count];i++)
{
Stock *aBookTemp = [retrievedArray objectAtIndex:i];
NSString *temp = [aBookTemp valueForKey:@"BookName"];
[searchArray addObject:temp];
}
for (NSString *sTemp in searchArray)
{
NSRange titleResultsRange = [sTemp rangeOfString:searchText options:NSCaseInsensitiveSearch];
if (titleResultsRange.length > 0)
[copyListOfItems addObject:sTemp];
}
[searchArray release];
searchArray = nil;
}
Пожалуйстапредложить несколько подходящих исправлений.