2

約300.000エントリのデータセットを取得しました。そのデータを保存するために、私はmongodb2.2.3の現在のバージョンを使用しています。私の質問は、集約フレームワークを使用して検索のパフォーマンスを向上させる方法ですか?

これは私の保存されたデータの例です:

{
    "_id":"654311649875645643131564",
    "@type":"K",
    "dataSourceA":{
        "name": "abc",
        "price": 12.99
    },
    "dataSourceB":{
        "name": "xyz"
    }
}

新しいバージョンのmongodbに切り替える前に、次のような集計フレームワークを使用せずに、たとえば最大値の検索を処理しました。

searchQuery = new BasicDBObject("dataSourceA.price", -1);
DBCursor cursor = collection.find().sort(searchQuery).limit(1);

この操作には約0.921 secs

今、私は同じ結果を達成するために集約フレームワークを試しましたが、最大価格をより早く見つけたいと思います。これが私のアプローチです:

DBObject match = new BasicDBObject("$match", new BasicDBObject("@type", "K"));
DBObject fields = new BasicDBObject("dataSourceA.price", 1);          
DBObject project = new BasicDBObject("$project", fields);
DBObject groupFields = new BasicDBObject("_id", 1);
groupFields.put("max", new BasicDBObject("$max", "$dataSourceA.price"));

DBObject group = new BasicDBObject("$group", groupFields);

Iterable<DBObject> results = 
    collection.aggregate(match, project, group).results();

しかし、この操作4.837 secsは最大価格を見つけようとしている必要があります。では、私のクエリで何を改善できるでしょうか?このようなデータベースは、Javaでカーソルを繰り返すよりも高速である必要があると思いました。間違っている場合は、修正してください。

4

1 に答える 1

1

これにはいくつかの理由があります。

まず、カーソルの例では、サブドキュメントフィールドのすべてのルートドキュメントを並べ替えるクエリを実行しているだけです。ほとんどの場合、インデックスが付けられています。これは、どのように見ても高速になります。

2番目$maxは実際には$group演算子です。これは、クエリセットに適合するすべてのドキュメント(300,000個すべて)に対するメモリ内操作であるため、MongoDBは、にグループ化されたドキュメントごとの複数値フィールドの最大値を計算しています_id。結果セット内のすべてのドキュメント。

どのように機能するか$maxによって、インデックス付きカーソルから得られる即時の並べ替え機能が即座に失われます。

それだけでなく、集約の途中で投影しているため、MongoDBはドキュメントをさらに強制的に分割します。

したがって、ソートされたインデックス付きカーソルを反復処理するよりも高速であってはなりません。

于 2013-03-14T10:35:00.370 に答える