搜索核心数据而不获取所有行

时间:2014-06-06 01:21:49

标签: search core-data large-data

我的核心数据有+2百万行,我想搜索两个特定字段:name&电话(例如)。我在搜索栏中为每个字段插入范围。如果我没有庞大的数据集,一切都会好起来的。这就是为什么我想在搜索控制器之前搜索我的核心数据而不加载内存中的所有行的原因。当我的搜索文本长度> 1时,只需要一个结果3或单击“搜索”按钮时。

  1. 我只有一个带有搜索栏的表格视图
  2. 当AppDidFinish与通话记录plist
  3. 时,我会填充
  4. 当搜索栏isActive时,我的应用程序会自动加载,直到加载了2百万行。我需要避免这一步并继续前进到第4步
  5. 输入搜索文本。然后结果filteredArray显示在表视图
  6. ...

    如果有任何想法,我会表示赞赏。

    这里有一些代码:

    - (NSFetchedResultsController *)fetchedResultsController
    {
        if (_fetchedResultsController != nil) {
            return _fetchedResultsController;
        }
        NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
        NSEntityDescription *entity = [NSEntityDescription entityForName:@"Guia" inManagedObjectContext:self.managedObjectContext];
        [fetchRequest setEntity:entity];
    
        [fetchRequest setFetchBatchSize:50];
    
        NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"name" ascending:NO];
        NSArray *sortDescriptors = @[sortDescriptor];
    
        [fetchRequest setSortDescriptors:sortDescriptors];
    
        NSFetchedResultsController *aFetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest managedObjectContext:self.managedObjectContext sectionNameKeyPath:nil cacheName:@"GuiaCache"];
        aFetchedResultsController.delegate = self;
        self.fetchedResultsController = aFetchedResultsController;
    
        NSError *error = nil;
        if (![self.fetchedResultsController performFetch:&error]) {
            abort();
        }
    
        return _fetchedResultsController;
    }
    

    也许在这种方法中我需要改进一些谓词

    - (NSFetchRequest *)searchFetchRequest
    {
        if (_searchFetchRequest != nil) {
            return _searchFetchRequest;
        }
    
        _searchFetchRequest = [[NSFetchRequest alloc] init];
        NSEntityDescription *entity = [NSEntityDescription entityForName:@"Guia" inManagedObjectContext:self.managedObjectContext];
        [_searchFetchRequest setEntity:entity];
    
        [_searchFetchRequest setFetchBatchSize:50];
    
        NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"name" ascending:NO];
        NSArray *sortDescriptors = [NSArray arrayWithObjects:sortDescriptor, nil];
        [_searchFetchRequest setSortDescriptors:sortDescriptors];
    
        return _searchFetchRequest;
    }
    

    最后在Core Data中搜索的两个函数

    - (void)filterContentForSearchText:(NSString*)searchText scope:(NSString*)scope
    {
        if ([searchText length] > 3)
            [self searchForText:searchText scope:_scopeKeyIndex];
    }
    
    - (void)searchForText:(NSString *)searchText scope:(NSUInteger)scopeOption
    {
        if (self.managedObjectContext)
        {
            NSString *predicateFormat = @"%K BEGINSWITH[cd] %@";
            NSString *searchAttribute = @"telephone";
    
            if (scopeOption == 1)
            {
                searchAttribute = @"name";
            }
    
            NSPredicate *predicate = [NSPredicate predicateWithFormat:predicateFormat, searchAttribute, searchText];
            [self.searchFetchRequest setPredicate:predicate];
    
            NSError *error = nil;
            _filteredList = [self.managedObjectContext executeFetchRequest:self.searchFetchRequest error:&error];
        }
    }
    

    如果您需要其他一些代码,请发表评论。

1 个答案:

答案 0 :(得分:0)

首先,针对您的应用程序运行Instruments,特别是Time Profiler。它说时间花在哪里?

你的搜索中有谓词吗?谓词是什么样的?您需要显示一些代码供人们帮助。

对200万条记录进行抓取需要花费一些时间,但我怀疑它没有将200万行加载到内存中,因为这很可能会导致内存问题以及速度问题。

发布Time Profiler的结果,让我们看看花费的时间。

更新

首先你的谓词非常昂贵。如果可能的话,应该避免BEGINSWITH。使案例和变音符号不敏感会增加成本。

您是否针对代码运行了仪器?你运行时间分析器了吗?没有跑步,你只是在猜测。您需要运行时间分析器,如果没有链接到整个配置文件,至少会显示结果。