MongoDB
 Computer >> コンピューター >  >> プログラミング >> MongoDB

MongoDBで内部配列内の特定オブジェクトの合計値に基づいてソートする方法

MongoDBで、内部配列に含まれる特定のオブジェクトの合計値に基づいてドキュメントをソートしたい場合は、$match$sortと組み合わせた集計パイプライン(aggregate)を活用します。本記事では、実際のサンプルコードを交えながら、その具体的な手順をわかりやすく解説します。

サンプルコレクションの作成

まず、ドキュメントを含むコレクションを作成しましょう。以下の例では、demo189というコレクションに、Listという内部配列を持つドキュメントを挿入します。

> db.demo189.insertOne(
...   {
...      "_id" : 100,
...      "List" : [
...         {
...            "Value" : 10
...         },
...         {
...            "Value" : 20
...         },
...         {
...            "Value" : 10
...         }
...      ]
...   }
...);
{ "acknowledged" : true, "insertedId" : 100 }
> db.demo189.insertOne(
...   {
...      "_id" : 101,
...      "List" : [
...         {
...            "Value" : 10
...         },
...         {
...            "Value" : 10
...         },
...         {
...            "Value" : 10
...         }
...      ]
...   }
...);
{ "acknowledged" : true, "insertedId" : 101 }

挿入したドキュメントの確認

find()メソッドを使って、コレクション内のすべてのドキュメントを表示してみましょう。

> db.demo189.find();

このクエリを実行すると、次のような出力が得られます。

{ "_id" : 100, "List" : [ { "Value" : 10 }, { "Value" : 20 }, { "Value" : 10 } ] }
{ "_id" : 101, "List" : [ { "Value" : 10 }, { "Value" : 10 }, { "Value" : 10 } ] }

内部配列の特定オブジェクトの合計でソートするクエリ

ここからが本題です。内部配列内の特定の値(この例ではValue: 10)の出現回数を合計として計算し、その合計値で降順にソートします。処理の流れは以下のとおりです。

  1. $unwind:配列Listを展開し、各要素を個別のドキュメントとして扱います。
  2. $group_idでグループ化し、$cond$eqを組み合わせてValueが10である要素の数を$sumでカウントします。同時に、$pushで元の配列構造も保持します。
  3. $sort:計算した合計値(total)の降順でソートします。
  4. $project:出力にListフィールドのみを含めます。

具体的なクエリは以下のとおりです。

> db.demo189.aggregate([
...   { "$unwind" : "$List" },
...   { "$group" : {
...      "_id" : "$_id",
...      "total" : {
...         "$sum" : {
...            "$cond" : {
...               "if" : { "$eq" : [ "$List.Value", 10 ] },
...               "then" : 1,
...               "else" : 0
...            }
...         }
...      },
...      "List" : {
...         "$push" : {
...            "Value" : "$List.Value"
...         }
...      }
...   }},
...   { "$sort" : { "total" : -1 } },
...   { "$project" : {
...      "List" : 1
...   }}
...])

実行結果

このクエリを実行すると、以下のような出力が得られます。

{ "_id" : 101, "List" : [ { "Value" : 10 }, { "Value" : 10 }, { "Value" : 10 } ] }
{ "_id" : 100, "List" : [ { "Value" : 10 }, { "Value" : 20 }, { "Value" : 10 } ] }

結果の解説

ドキュメント_id: 101は配列内にValue: 10が3つ含まれているため合計は3、一方ドキュメント_id: 100は2つしか含まれていないため合計は2です。そのため、合計値が大きい_id: 101が先頭に表示されています。このように、$unwind$group$sum$cond$sortを組み合わせることで、内部配列内の特定オブジェクトの合計に基づいた柔軟なソートが実現できます。

  1. MongoDBでネストされた配列をソートする方法:$unwindと$sortを活用したクエリ

    MongoDBでドキュメント内に格納されたネストされた配列(サブドキュメントの配列)をソートしたい場合、集計パイプライン(aggregate)を使い、$unwindで配列を展開した後に$sortで並べ替え、最後に$groupで再構成するのが定番のアプローチです。この記事では、実際にコレクションを作成しながら、ネストされた配列をスコア順にソートする手順を解説します。1. サンプルコレクションの作成まず、ネストされた配列「details」を持つドキュメントを挿入してコレクションを作成します。> db.demo505.insertOne( ... { ... details: [ ..

  2. MongoDBでオブジェクトの配列内の複数条件に一致するドキュメントを検索する方法($andと$regex活用)

    MongoDBでオブジェクト(サブドキュメント)の配列内から、複数の条件を同時に満たすドキュメントを検索したい場合は、$and演算子と$regex演算子、さらに$elemMatchを組み合わせるのが効果的です。$andは、1つ以上の式からなる配列に対して論理AND演算を実行し、配列内のすべての条件を満たすドキュメントだけを選択します。また、$elemMatchを使うことで、配列内の同一要素が複数条件を満たすかどうかを正確に判定できます。サンプルコレクションの作成まず、検証用のコレクションを作成してドキュメントを挿入してみましょう。> db.demo525.insertOne({detai