MongoDBでフィールドの重複(非ユニーク)値をすべて検索する方法
MongoDBで重複した値を見つけるには?
MongoDBであるフィールドに重複した(非ユニークな)値が存在するかどうかを調べたい場合、aggregate()メソッドを使うのが効果的です。distinct()メソッドは一意な値の一覧を返しますが、逆に「どの値が何回登場しているのか」を確認したいときは、$group演算子と$match演算子を組み合わせた集計パイプラインが便利です。ここでは、まずサンプルコレクションを作成し、その後重複値を抽出するクエリを実行してみましょう。
1. ドキュメントを含むコレクションを作成する
まず、insertOne()メソッドを使ってコレクション「findAllNonDistinctDemo」にドキュメントを挿入します。意図的に同じUserNameを持つドキュメントを複数登録しています。
> db.findAllNonDistinctDemo.insertOne({"UserName":"John","UserAge":28});
{
"acknowledged" : true,
"insertedId" : ObjectId("5c995078863d6ffd454bb647")
}
> db.findAllNonDistinctDemo.insertOne({"UserName":"Larry","UserAge":21});
{
"acknowledged" : true,
"insertedId" : ObjectId("5c995081863d6ffd454bb648")
}
> db.findAllNonDistinctDemo.insertOne({"UserName":"Larry","UserAge":23});
{
"acknowledged" : true,
"insertedId" : ObjectId("5c995089863d6ffd454bb649")
}
> db.findAllNonDistinctDemo.insertOne({"UserName":"David","UserAge":22});
{
"acknowledged" : true,
"insertedId" : ObjectId("5c995093863d6ffd454bb64a")
}
> db.findAllNonDistinctDemo.insertOne({"UserName":"John","UserAge":26});
{
"acknowledged" : true,
"insertedId" : ObjectId("5c99509d863d6ffd454bb64b")
}
> db.findAllNonDistinctDemo.insertOne({"UserName":"Robert","UserAge":24});
{
"acknowledged" : true,
"insertedId" : ObjectId("5c9950a7863d6ffd454bb64c")
}
> db.findAllNonDistinctDemo.insertOne({"UserName":"Robert","UserAge":25});
{
"acknowledged" : true,
"insertedId" : ObjectId("5c9950b1863d6ffd454bb64d")
}
> db.findAllNonDistinctDemo.insertOne({"UserName":"Mike","UserAge":29});
{
"acknowledged" : true,
"insertedId" : ObjectId("5c9950bc863d6ffd454bb64e")
}2. find()メソッドですべてのドキュメントを表示する
find()メソッドを使うと、コレクション内のすべてのドキュメントを確認できます。
> db.findAllNonDistinctDemo.find().pretty();
上記のクエリを実行すると、次のような出力が得られます。
{
"_id" : ObjectId("5c995078863d6ffd454bb647"),
"UserName" : "John",
"UserAge" : 28
}
{
"_id" : ObjectId("5c995081863d6ffd454bb648"),
"UserName" : "Larry",
"UserAge" : 21
}
{
"_id" : ObjectId("5c995089863d6ffd454bb649"),
"UserName" : "Larry",
"UserAge" : 23
}
{
"_id" : ObjectId("5c995093863d6ffd454bb64a"),
"UserName" : "David",
"UserAge" : 22
}
{
"_id" : ObjectId("5c99509d863d6ffd454bb64b"),
"UserName" : "John",
"UserAge" : 26
}
{
"_id" : ObjectId("5c9950a7863d6ffd454bb64c"),
"UserName" : "Robert",
"UserAge" : 24
}
{
"_id" : ObjectId("5c9950b1863d6ffd454bb64d"),
"UserName" : "Robert",
"UserAge" : 25
}
{
"_id" : ObjectId("5c9950bc863d6ffd454bb64e"),
"UserName" : "Mike",
"UserAge" : 29
}3. aggregate()で重複している値を抽出する
いよいよ本題です。次のクエリでは、aggregate()メソッドの中で$groupによりUserNameごとの出現回数(Counter)を集計し、続く$matchでCounterが2以上($gt: 1)のものだけを絞り込んでいます。これにより、重複している値のみを取り出せます。
> db.findAllNonDistinctDemo.aggregate([
... { "$group": {
... "_id": "$UserName",
... "Counter": { "$sum": 1 }
... }},
... { "$match": {
... "Counter": { "$gt": 1 }
... }}
... ]).pretty();実行すると、次のような結果が出力されます。
{ "_id" : "Robert", "Counter" : 2 }
{ "_id" : "Larry", "Counter" : 2 }
{ "_id" : "John", "Counter" : 2 }まとめ
このように、aggregate()メソッドで$groupと$matchを組み合わせることで、MongoDBのコレクション内に存在する重複した値と、その出現回数を簡単に特定できます。データのクレンジングや一意制約の導入前の調査などに役立つテクニックなので、ぜひ活用してください。
-
MongoDBでフィールドの戻り値を制限するクエリの書き方($slice演算子の使い方)
MongoDBでフィールドの戻り値を制限するクエリの書き方MongoDBで配列フィールドの要素数を制限して取得したい場合は、$slice演算子を使用します。この演算子を活用することで、クエリ結果として返す配列の要素数を柔軟にコントロールできます。ここでは、具体的な手順をサンプルコードとともに解説します。1. コレクションとドキュメントの作成まず、insertOne()メソッドを使ってドキュメントを挿入し、コレクションを作成します。> db.demo594.insertOne(... {... &n
-
MongoDBで特定の文字列を使ってフィールドのすべての値を一括更新する方法
MongoDBでフィールドのすべての値を一括更新する方法MongoDBのコレクション内に存在するすべてのドキュメントの特定フィールドを、同じ文字列でまとめて更新したい場合があります。そのようなときは、update()メソッドにオプション「multi: true」を指定します。この記事では、実際のコマンド例をもとに、手順をわかりやすく解説します。1. サンプルコレクションの作成まずはinsertOne()メソッドを使って、テスト用コレクション「demo720」に複数のドキュメントを挿入します。> db.demo720.insertOne({SubjectName:MySQL}); {