0

OS X 的Search Kit Framework允许创建和访问搜索索引。但是,如果该索引的名称未知,则无法访问现有的搜索索引。可用于访问现有搜索索引的框架的所有功能(SKIndexOpenWithData、SKIndexOpenWithMutableData、SKIndexOpenWithURL)都要求提供索引名称。这与存储搜索索引数据的文件的文件名不同。

当我尝试在不知道索引名称的情况下调用 SKIndexOpenWithURL 来访问现有搜索索引文件时,该函数不会返回有效的 SKIndexRef。将 NULL 作为索引名称传递(如框架文档所建议的那样)不起作用,因为 Search Kit 框架仅尝试使用索引名称“IADefaultIndex”。

例如,如果我创建一个索引名称如下的索引文件:

    NSString *path = @"/Users/Tim/Desktop/searchindex.skindex";
    NSURL *url = [NSURL fileURLWithPath: path];  
    NSString *name = @"myIndex";          
    SKIndexType type = kSKIndexInverted;                    
    SKIndexRef skIndex;
    skIndex = SKIndexCreateWithURL ((__bridge CFURLRef)url, (__bridge CFStringRef)name, (SKIndexType)type, (CFDictionaryRef)NULL);
    // ..

如果我知道索引名称“myIndex”,我以后只能打开文件并访问存储的索引。如果我尝试在没有(或不知道)索引名称的情况下打开文件,则以下代码示例将失败:

    NSURL *skURL = [NSURL fileURLWithPath:@"/Users/Tim/Desktop/searchindex.skindex"];
    SKIndexRef skIndex;
    skIndex = SKIndexOpenWithURL((__bridge CFURLRef)skURL, NULL, true);
    if (!skIndex) NSLog (@"couldn't open index!");

但是,搜索索引的名称肯定在该索引文件中。有人知道在不知道搜索索引名称的情况下检索该名称或以其他方式访问搜索索引文件的方法吗?我知道根据框架文档,不可能使用框架来获取该索引名称,但它仍然应该是可能的。

4

2 回答 2

2

好的,经过一番研究,我想出了如何从搜索索引文件中提取索引名称:

-(NSString*)getIndexNameOfSKFile:(NSString*)filePath
{
    if (!filePath) return nil;

    // open the search index file
    NSData *data = [NSData dataWithContentsOfFile:filePath];
    if (!data) return nil;
    NSUInteger dataLength = [data length];

    // calculate the offset where the index name is stored
    int32_t offset1, offset2;
    if (dataLength<11) return nil;
    [data getBytes:&offset1 range:NSMakeRange(4,4)];
    [data getBytes:&offset2 range:NSMakeRange(8,4)];
    int32_t offset = CFSwapInt32HostToBig(offset1)+(CFSwapInt32HostToBig(offset2)/2)+14;

    // Get index name string (stored as zero-terminated string)
    unichar c;
    NSMutableString *indexName = [NSMutableString stringWithCapacity:0];
    do {
        if (dataLength<(offset+1)) return nil;
        [data getBytes:&c range:NSMakeRange(offset, 2)];
        if (c!=0) [indexName appendString:[NSString stringWithCharacters:&c length:1]];
        offset+=2;
    } while (c!=0);
    return indexName;
}

这可能不适用于每个 OS X 版本,但它适用于 10.7。

于 2012-06-18T16:25:49.023 回答
1

您确定是没有索引名称导致问题,而不是代码的其他部分,例如有效的 URL?正如您所注意到的,文档说它应该在不知道索引名称的情况下工作。我已经广泛使用 Search Kit 并且从来不需要它,这就是为什么我怀疑问题可能是其他问题。

你可以发布一些代码吗?

要回答有关是否可以从索引中获取名称的问题,方法 SKIndexCreateWithURL 的文档说不:

inIndexName 索引的名称。如果在 inIndexName 设置为 NULL 的情况下调用此函数,Search Kit 会为索引分配默认索引名称 IADefaultIndex。如果您随后尝试在同一文件中创建第二个索引而不指定名称,则不会创建第二个索引并且此函数返回 NULL。Search Kit 目前不支持从索引中检索索引名称

如果您在 Cocoa 领域工作,我想邀请您使用我的开源 Search Kit 包装器。你会在 Github 上找到代码:

https://github.com/phildow/SPSearchStore

如果您可以发布一些代码,我很乐意看看它。

于 2012-06-17T01:46:40.443 回答