sql >> データベース >  >> NoSQL >> MongoDB

MongoDB正規表現、インデックス、パフォーマンス

    MongoDBは、$regex演算子を使用した正規表現をサポートしています。ただし、これらのMongoDB正規表現クエリには欠点があります。1つのタイプを除くすべての正規表現では、インデックスの使用が不十分であり、パフォーマンスの問題が発生します。大量のデータを含む本番サーバーの場合、正規表現クエリが不適切な場合、サーバーがひざまずく可能性があります。

    MongoDB正規表現ベースのクエリは、MongoDBを使用するほとんどのアプリケーションでかなり一般的なクエリです。これは、ほとんどのリレーショナルデータベースでサポートされている「LIKE」操作に似ています。コマンドの構文は次のとおりです

    { $regex: /pattern/, $options: '<options>' }
    E.g. { name: { $regex: /^acme.*test/}}
    

    正規表現操作と追加オプションの詳細については、MongoDBのドキュメントを参照してください

    この説明の残りの部分では、照合するフィールドにインデックスがあると想定します。インデックスを作成しないと、コレクションスキャンが実行され、パフォーマンスが大幅に低下します。ただし、フィールドにインデックスが付けられている場合でも、パフォーマンスが低下する可能性があります。その理由は、正規表現が「プレフィックス式」である場合にのみ、MongoDBがインデックスを有効に活用できるためです。これらは、「^」文字で始まる式です。

    例えば。 {名前:{$ regex:/ ^ acme /}}

    これにより、MongoDBは、このクエリに関連するインデックスエントリの範囲を識別し、効率的なクエリを実現できます。 MongoDBはスキャンをインデックスエントリの範囲に絞り込むことができないため、他のクエリではインデックススキャンが発生します。すべてのインデックスをメモリにページングする必要があり、これがサーバーのワーキングセットに影響を与えるため、インデックススキャンは特に悪いです(実際、インデックススキャンは、コレクションスキャンよりもパフォーマンスが低下する可能性があり、ページフォールトの数が2倍になります。 。

    いくつかの例と結果のクエリプランを見てみましょう。テストの目的で、100kのドキュメントを含むコレクションを設定しました。各ドキュメントには、16文字の文字列であるfirstNameフィールドがあります。

    例1:{名前:{$ regex:/ ^ acme /}}
    結果:効率的なインデックスの使用
    クエリプラン:

    executionStats" : {
           "executionSuccess" : true,
           "nReturned" : 0,
           "executionTimeMillis" : 0,
           "totalKeysExamined" : 1,
           "totalDocsExamined" : 0,
    

    例2:{名前:{$ regex:/ ^ acme / i}}
    結果:大文字と小文字を区別しない要件のため、インデックススキャンが非効率的です。したがって、基本的に/ iオプションは「プレフィックス式」を無効にします
    クエリプラン:

            "executionStats" : {
                    "executionSuccess" : true,
                    "nReturned" : 0,
                    "executionTimeMillis" : 137,
                    "totalKeysExamined" : 100000,
                    "totalDocsExamined" : 0,
    

    例3:{名前:{$ regex:/acme.*corp/}}
    結果:非効率的なインデックススキャン
    クエリプラン:

                    "executionSuccess" : true,
                    "nReturned" : 0,
                    "executionTimeMillis" : 167,
                    "totalKeysExamined" : 100000,
                    "totalDocsExamined" : 0,
    

    例4:{名前:{$ regex:/ acme /}}
    結果:非効率的なインデックススキャン

            "executionStats" : {
                    "executionSuccess" : true,
                    "nReturned" : 0,
                    "executionTimeMillis" : 130,
                    "totalKeysExamined" : 100000,
                    "totalDocsExamined" : 0,
    

    1. MongoDB $ orderBy

    2. マングースからコレクションのリストを取得しようとしています

    3. 日付部分を返すためのMongoDB集計演算子

    4. マングースはインターネットなしでは接続できません