3

ユーザーのiCloudフォルダにあるディレクトリのリストを取得しようとしています。特別な種類のファイル(txtファイルなど)を探す方法を考えましたが、正常に機能します。

NSMetadataQuery *query = [[NSMetadataQuery alloc] init];
_query = query;

//Search all files in the Documents directories of the application’s iCloud container directories:
[query setSearchScopes:[NSArray arrayWithObject:NSMetadataQueryUbiquitousDocumentsScope]]; 

NSPredicate *pred = [NSPredicate predicateWithFormat:@"%K ENDSWITH '.txt'", NSMetadataItemFSNameKey];

[query setPredicate:pred];
[query startQuery];

ただし、現在はディレクトリのみを取得しようとしています。NSPredicateに関するドキュメントを読みましたが、ディレクトリを探す方法がわかりません。NSPredicateはこのために作られていないと思いますか?何かが次のようなディレクトリであるかどうかを確認できます。

    BOOL isDir;
BOOL exists = [fm fileExistsAtPath:path isDirectory:&isDir];
if (exists) {
    /* file exists */
    if (isDir) {
        /* file is a directory */
    }
 }

しかし、これをNSMetadataQueryに適用する方法は、私にはわかりません。私は私が得ることができるどんな助けにも感謝するでしょう。


編集:

述語をに変更しました[NSPredicate predicateWithFormat:@"%K.pathExtension = ''", NSMetadataItemFSNameKey];

次に、クエリがいつ終了するかを次のように判断します。

    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(queryDidFinishGathering:) name:NSMetadataQueryDidFinishGatheringNotification object:query];
[query startQuery];

- (void)queryDidFinishGathering:(NSNotification *)notification {

NSMetadataQuery *query = [notification object];
[query disableUpdates]; // You should invoke this method before iterating over query results that could change due to live updates.
[query stopQuery]; // You would call this function to stop a query that is generating too many results to be useful but still want to access the available results.

[self loadData:query];
[[NSNotificationCenter defaultCenter] removeObserver:self name:NSMetadataQueryDidFinishGatheringNotification object:query];
_query = nil; // we're done with it

}

そして最後に、カウントを行いますが、これにより、クラウドにあるディレクトリの数に関係なく、常に0が得られます(LionおよびMobile Documentsフォルダーを介してこれを確認しました。たとえば、Documents / myTXTなどがあります)。これは非常に奇妙です。テキストファイルを数えると、4つのtxtファイルがあるので4つになります。だから私は私のディレクトリが数えられていないと思います:

 - (void)loadData:(NSMetadataQuery *)query {

    NSLog(@"Query count %i", [query resultCount]);

...
4

4 に答える 4

7

EmptyStackの答えを運がなくて試しました。

私はそれNSMetadataQueryがディレクトリを見つけられないことを発見しました、問題は結果からディレクトリをフィルタリングすることではありませんNSPredicate、問題は単にクエリがフォルダを見つけられないことです。デバッガーを試してみたところ、見つかったものはすべてLBItemディレクトリではなく通常のファイルであることがわかりました。Appleが将来これを改善することを願っています。 たぶんMountainLionでは、フォルダをサポートしているように見えるので、これはより良いでしょう...おっと、それはまだNDAなので、ここでは読んでいません。忘れてください

ただし、これを回避する方法は少なくとも1つあります。

たとえば、ファイル構造が次の場合。

|_Folder
| |_file
| |_file2
|_Folder1
| |_file
|_file

そして、述語でクエリを作成します。

predicateWithFormat:@"%K LIKE '*'", NSMetadataItemFSNameKey

結果は次のようになります(NSMetadataItemURLKeyURLの取得に使用)

path/to/iCloud/Documents/Folder/file
path/to/iCloud/Documents/Folder/file2
path/to/iCloud/Documents/Folder1/file
path/to/iCloud/Documents/file

私たちがする必要があるのは、各URLのコンポーネントの数を調べ、必要に応じてURLを切り刻むことによって、これらの結果を自分でフィルタリングすることです。最初のレベルのアイテムには、、numberOfComponentsOfUbiquitousContainer + 1次のレベルにはさらに1つ、というようになります。繰り返しも破棄する必要があります(または、この例のようにFolder2回取得します)。

おそらく最適ではありませんが、私にとってはうまくいきます、

アップデート:

以下の述語を使用すると、サブフォルダーをクロールするときのクエリ結果が減少します。

// dirPath is an NSString path of the directory you want
// to look at. Usually, for the top level directory:
// [NSFileManager URLForUbiquityContainerIdentifier:nil].path;
predicateWithFormat:@"%K BEGINSWITH %@", NSMetadataItemPathKey, dirPath];
于 2012-05-09T06:20:19.207 に答える
2

ディレクトリのみを取得する場合は、次の述語を使用します。

predicateWithFormat:@"%K.pathExtension = ''", NSMetadataItemFSNameKey

拡張子のないファイル(私はいくつか見たことがあります)があるので、これはこの方法を使用してディレクトリのみを取得することを保証するものではないことに注意してください。ただし、すべてのファイルに拡張子が付いていることが確実な場合は、これを非常にうまく使用できます。

拡張子に関係なくすべてのファイルを取得する場合は、上記の述語にNOTキーワードを追加するだけです。

predicateWithFormat:@"NOT %K.pathExtension = ''", NSMetadataItemFSNameKey
于 2011-10-24T10:23:47.847 に答える
0

これは、NSMetadataqueryが使用する「実際の」コードであるMDQueryを使用して実行できます。

ターミナルで「mdls」と入力し、フォルダにドラッグします。次に、mdfindと入力し、提供されている例を使用して、kMDItemContentTypeタイプツリーをpublic.folderに変更するだけです。多くの結果が得られます。

次に、コードでこれを行うには、MDQueryRefの例に従う必要があります。コードフローはCocoaのものと同じであり、クエリの作成と理解がはるかに簡単であることがわかりました。cocoaコールバックをMDQueryに設定できるので、NSMetadataqueryとの互換性がかなり低下します。

NSMetadataQueryには、MDQueryにはないと思うiCloudのものがいくつかあります。ですから、それらは同一ではないと思います。

于 2012-06-04T19:57:44.437 に答える
-1

これを試して:

[query setPredicate:[NSPredicate predicateWithFormat:@"%K like '*.txt'", NSMetadataItemFSNameKey]];

わたしにはできる。

于 2011-10-28T08:20:51.303 に答える