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

RailsとMongoidのユニークな結果

    個別を使用してドキュメント(またはサブセット)を単純に返すことはできません。 ドキュメント による 指定されたキーに基づいて、個別の値の配列のみを返します。ただし、map-reduceを使用してこれを実現できます

    var _map = function () {
        emit(this.hash.call_id, {doc:this});
    }
    
    var _reduce = function (key, values) {
        var ret = {doc:[]};
        var doc = {};
        values.forEach(function (value) {
        if (!doc[value.doc.hash.call_id]) {
               ret.doc.push(value.doc);
               doc[value.doc.hash.call_id] = true; //make the doc seen, so it will be picked only once
           }
        });
        return ret;
    }
    

    上記のコードは自明です。マップ関数では、キーhash.call_idでグループ化しています。 ドキュメント全体を返して、関数を減らして処理できるようにします。

    削減機能では、グループ化された結果セットをループして、グループ化されたセットから1つのアイテムのみを選択します(複数の重複するキー値の中から-個別のシミュレーション)。

    最後にいくつかのテストデータを作成します

    > db.disTest.insert({hash:{call_id:"1234"},something:"AAA"})
    > db.disTest.insert({hash:{call_id:"1234"},something:"BBB"})
    > db.disTest.insert({hash:{call_id:"1234"},something:"CCC"})
    > db.disTest.insert({hash:{call_id:"5555"},something:"DDD"})
    > db.disTest.insert({hash:{call_id:"5555"},something:"EEE"})
    > db.disTest.find()
    { "_id" : ObjectId("4f30a27c4d203c27d8f4c584"), "hash" : { "call_id" : "1234" }, "something" : "AAA" }
    { "_id" : ObjectId("4f30a2844d203c27d8f4c585"), "hash" : { "call_id" : "1234" }, "something" : "BBB" }
    { "_id" : ObjectId("4f30a2894d203c27d8f4c586"), "hash" : { "call_id" : "1234" }, "something" : "CCC" }
    { "_id" : ObjectId("4f30a2944d203c27d8f4c587"), "hash" : { "call_id" : "5555" }, "something" : "DDD" }
    { "_id" : ObjectId("4f30a2994d203c27d8f4c588"), "hash" : { "call_id" : "5555" }, "something" : "EEE" }
    

    このマップReduceを実行すると

    > db.disTest.mapReduce(_map,_reduce, {out: { inline : 1}})
    {
        "results" : [
            {
                "_id" : "1234",
                "value" : {
                    "doc" : [
                        {
                            "_id" : ObjectId("4f30a27c4d203c27d8f4c584"),
                            "hash" : {
                                "call_id" : "1234"
                            },
                            "something" : "AAA"
                        }
                    ]
                }
            },
            {
                "_id" : "5555",
                "value" : {
                    "doc" : [
                        {
                            "_id" : ObjectId("4f30a2944d203c27d8f4c587"),
                            "hash" : {
                                "call_id" : "5555"
                            },
                            "something" : "DDD"
                        }
                    ]
                }
            }
        ],
        "timeMillis" : 2,
        "counts" : {
            "input" : 5,
            "emit" : 5,
            "reduce" : 2,
            "output" : 2
        },
        "ok" : 1,
    }
    

    個別セットの最初のドキュメントを取得します。最初にmap/reduce関数を文字列化し、このようにmapreduceを呼び出すことで、mongoidでも同じことができます

      MyObject.collection.mapreduce(_map,_reduce,{:out => {:inline => 1},:raw=>true })
    

    お役に立てば幸いです




    1. MongoDBネストされたオブジェクトの集計カウント

    2. mongodbまたはcassandraを使用した空間データ

    3. Redis-エラー:値は有効なfloatではありません

    4. MongoDBのインデックス