MongoDB での大文字と小文字を区別しないクエリ

Tahseen Tauseef 2024年2月15日
  1. MongoDB での大文字と小文字を区別しないクエリ
  2. 大文字と小文字を区別しない正規表現クエリを改善する
  3. MongoDB で大文字と小文字を区別しない検索に find() メソッドで正規表現を使用する
MongoDB での大文字と小文字を区別しないクエリ

この記事では、大文字と小文字を区別しないクエリについて簡単に説明します。 さらに、大文字と小文字を区別しない検索クエリについても詳しく説明されています。

この記事では、次のトピックについて説明します。

  1. 大文字と小文字を区別しないクエリ
  2. 大文字と小文字を区別しない正規表現クエリを改善する
  3. 大文字と小文字を区別しない検索には、find() メソッドで正規表現を使用します

MongoDB での大文字と小文字を区別しないクエリ

大文字と小文字を区別しないインデックスを使用すると、大文字と小文字を区別せずに文字列を比較する検索が可能になります。

db.collection.createIndex() を使用すると、オプションのパラメーターとして collation パラメーターを含めることで、大文字と小文字を区別しないインデックスを作成できます。

db.collection.createIndex( { "key" : 1 },
                           { collation: {
                               locale : <locale>,
                               strength : <strength>
                             }
                           } )

大文字と小文字を区別するインデックスの照合順序を指定する場合は、次を含めます。

  1. locale - 言語規則を指定します。
  2. 強さ - 比較ルールを決定するために使用されます。 1 または 2 の値は、大文字と小文字を区別しない照合を示します。

行動:

大文字と小文字を区別しないインデックスを使用しても、クエリの結果には影響しません。 ただし、速度は向上します。

照合指定のインデックスを利用するには、クエリおよびソート操作でインデックスと同じ照合を使用する必要があります。 コレクションが照合を定義する場合、そのコレクションを使用するすべてのクエリとインデックスは、別の照合を指定しない限り、それを継承します。

大文字と小文字を区別しないインデックスを作成する

照合を使用してインデックスを作成し、strength オプションを 1 または 2 に指定して、デフォルトの照合なしでコレクションに大文字と小文字を区別しないインデックスを使用します。 インデックス レベルの照合を利用するには、クエリ レベルで同じ照合を提供する必要があります。

次の例では、デフォルトの照合を使用せずにコレクションを生成し、大文字と小文字を区別しない照合を使用してインデックスを type 列に追加します。

db.createCollection("fruit")

db.fruit.createIndex( { type: 1},
                      { collation: { locale: `en`, strength: 2 } } )

インデックスを使用するには、クエリに同じ照合順序が必要です。

db.fruit.insertMany( [
   { type: "bloctak" },
   { type: "Bloctak" },
   { type: "BLOCTAK" }
] )

db.fruit.find( { type: "bloctak" } )
//not use index, finds one result

db.fruit.find( { type: "bloctak" } ).collation( { locale: `en`, strength: 2 } )
// uses index, and will find three results

db.fruit.find( { type: "bloctak" } ).collation( { locale: `en`, strength: 1 } )
//not uses the index, finds three results

デフォルトの照合を使用したコレクションの大文字と小文字を区別しないインデックス

デフォルトの照合を使用してコレクションを確立すると、別の照合を指定しない限り、以降のすべてのインデックスはその照合を継承します。 照合を指定しないすべてのクエリは、デフォルトの照合を継承します。

以下の例では、デフォルトの照合で names コレクションを生成し、first_name フィールドでインデックスを作成します。

db.createCollection("names", { collation: { locale: `en_US`, strength: 2 } } )

db.names.createIndex( { first_name: 1 } ) // inherits the default collation

名前の小さなコレクションを挿入します。

db.names.insertMany( [
   { first_name: "Betsy" },
   { first_name: "BETSY"},
   { first_name: "betsy"}
] )

デフォルトでは、このコレクションに対するクエリは、指定された照合順序と、可能であればインデックスを使用します。

db.names.find( { first_name: "betsy" } )
// inherits the default collation: { collation: { locale: `en_US`, strength: 2 } }
// finds three results

前の手順では、コレクションの既定の照合順序を使用して 3つのドキュメントすべてを検出します。 効率を向上させるために、first_name フィールドにインデックスを採用しています。

このコレクションは、クエリで別の照合順序を指定することにより、大文字と小文字を区別する検索を引き続き実行できます。

db.names.find( { first_name: "betsy" } ).collation( { locale: `en_US` } )
// not use the collection`s default collation, finds one result

前の手順では、strength 値が指定されていない照合を使用しているため、1つのドキュメントのみが返されます。 インデックスまたはコレクションのデフォルトの照合は使用されません。

大文字と小文字を区別しない正規表現クエリを改善する

大文字と小文字を区別しない正規表現クエリ (I オプションを使用) を頻繁に行う場合は、検索に対応するために大文字と小文字を区別しないインデックスを作成する必要があります。

インデックスの照合を使用して、大文字と小文字の規則やアクセント記号の規則など、言語固有の文字列比較規則を提供できます。 大文字と小文字を区別しないインデックスにより、大文字と小文字を区別しないクエリのパフォーマンスが大幅に向上します。

employees コレクション内の次のドキュメントを検討してください。 通常の _id インデックスを除いて、このコレクションには他のインデックスは含まれていません。

db={
  "employees": [
    {
      "_id": 1,
      "first_name": "Hannah",
      "last_name": "Simmons",
      "dept": "Engineering"
    },
    {
      "_id": 2,
      "first_name": "Michael",
      "last_name": "Hughes",
      "dept": "Security"
    },
    {
      "_id": 3,
      "first_name": "Wendy",
      "last_name": "Crawford",
      "dept": "Human Resources"
    },
    {
      "_id": 4,
      "first_name": "MICHAEL",
      "last_name": "FLORES",
      "dept": "Sales"
    }
  ]
}

アプリケーションが first_name 列を頻繁に検索する場合は、大文字と小文字を区別しない正規表現クエリを使用して、一致する名前を検出することをお勧めします。

大文字と小文字を区別しない正規表現は、上記の例のように、MichaelMICHAEL の両方の first_name がある場合のように、異なるデータ形式との照合にも役立ちます。

ユーザーが michael を検索すると、プログラムは次のクエリを実行する可能性があります。

db.employees.find({
  first_name: {
    $regex: "michael",
    $options: "i"
  }
})

このクエリには $regex が含まれているため:

{ "_id" : 2, "first_name" : "Michael", "last_name" : "Hughes", "dept" : "Security" }
{ "_id" : 4, "first_name" : "MICHAEL", "last_name" : "FLORES", "dept" : "Sales" }

このクエリは目的のドキュメントを返しますが、大文字と小文字を区別しないインデックス サポートのない正規表現クエリは低速です。 first_name フィールドに大文字と小文字を区別しないインデックスを作成することで、効率を上げることができます。

db.employees.createIndex(
  { first_name: 1 },
  { collation: { locale: 'en', strength: 2 } }
)

インデックスの collation ドキュメントの strength フィールドが 1 または 2 に設定されている場合、インデックスは大文字と小文字を区別せず、照合ドキュメントとさまざまな strength 値をより詳細に説明します。

アプリケーションでこのインデックスを使用するには、クエリでインデックスの照合ドキュメントも指定する必要があります。 前の db.collection.find() 関数から $regex 演算子を削除し、代わりに新しく構築されたインデックスを使用します。

db.employees.find( { first_name: "michael" } ).collation( { locale: 'en', strength: 2 } )

クエリで大文字と小文字を区別しないインデックスを使用する場合は、$regex 演算子を使用しないでください。 $regex 実装は照合をサポートしておらず、大文字と小文字を区別しないインデックスを使用できません。

MongoDB で大文字と小文字を区別しない検索に find() メソッドで正規表現を使用する

大文字と小文字を区別しない検索には、find() メソッドで正規表現を使用します。

構文:

db.demo572.find({"yourFieldName" : { `$regex`:/^yourValue$/i}});

上記の構文を理解するために、ドキュメントのコレクションを作成してみましょう。

> db.demo572.insertOne({"CountryName":"US"});{
   "acknowledged" : true, "insertedId" : ObjectId("5e915f0e581e9acd78b427f1")
}
> db.demo572.insertOne({"CountryName":"UK"});{
   "acknowledged" : true, "insertedId" : ObjectId("5e915f17581e9acd78b427f2")
}
> db.demo572.insertOne({"CountryName":"Us"});{
   "acknowledged" : true, "insertedId" : ObjectId("5e915f1b581e9acd78b427f3")
}
> db.demo572.insertOne({"CountryName":"AUS"});{
   "acknowledged" : true, "insertedId" : ObjectId("5e915f20581e9acd78b427f4")
}
> db.demo572.insertOne({"CountryName":"us"});{
   "acknowledged" : true, "insertedId" : ObjectId("5e915f25581e9acd78b427f5")
}

find() 関数は、コレクション内のすべてのドキュメントを表示します。

db.demo572.find();

これにより、次の出力が生成されます。

MongoDB で大文字と小文字を区別しない検索

以下は、大文字と小文字を区別しない検索のクエリです。

> db.demo572.find({"CountryName" : { `$regex`:/^US$/i}});

これにより、次の出力が生成されます。

MongoDB 2 で大文字と小文字を区別しない検索

関連記事 - MongoDB Query