2014-01-24 3 views
2

특정 시간 간격을 기준으로 수집 물을 집계해야합니다.MongoDB에서 시간 간격별로 문서를 어떻게 집계 할 수 있습니까?

내가 생각하기에 예를 들어, 우리의 시간당 시간.

30 분 간격 (또는 기타)을 기준으로 집계해야합니다. 첫 번째 문서는 3:45 PM에 작성되었습니다. 그런 다음 3:45 PM과 4:15 PM 사이에 작성된 5 개의 문서가 더 있습니다. 그래서이 시간 간격에는 6 개의 문서가 있습니다. 따라서 MapReduce 결과의 첫 번째 문서는 카운트가 6 인 문서입니다.

다음 문서는 4:35 PM에 작성되고, 세 번째는 4:40 PM에 작성됩니다.

var map = function() {          
     var key = {name: this.name, minute: this.timestamp.getMinutes()}; 
     emit(key, {count: 1}) 
}; 

:

는 그래서 맵리 듀스 결과의 다음 문서

가 현재 내지도 기능은 다음과 같습니다 ... 등등 4.

와의 수와 문서입니다 그래서 특별한 것은 없습니다. 현재 나는 분 단위로 그룹화하고 있으며, 결국 원하는 것을 원하지 않습니다. 여기에서는 분 대신에 위에서 설명한 시간 간격을 확인할 수 있어야합니다.

그리고 내 감소 기능 :

var reduce = function(key, values) 
{ 
    var sum = 0; 
    values.forEach(function(value) 
    { 
     sum += value['count']; 
    }); 
    return {count: sum}; 
}; 

이의 출력은 그런 식입니다 :

{ 
0: "{ "_id" : { "name" : "A" , "minute" : 11.0} , "value" : { "count" : 1.0}}", 
1: "{ "_id" : { "name" : "B" , "minute" : 41.0} , "value" : { "count" : 6.0}}", 
2: "{ "_id" : { "name" : "B" , "minute" : 42.0} , "value" : { "count" : 3.0}}", 
3: "{ "_id" : { "name" : "C" , "minute" : 41.0} , "value" : { "count" : 2.0}}", 
4: "{ "_id" : { "name" : "C" , "minute" : 42.0} , "value" : { "count" : 2.0}}", 
5: "{ "_id" : { "name" : "D" , "minute" : 11.0} , "value" : { "count" : 1.0}}", 
6: "{ "_id" : { "name" : "E" , "minute" : 16.0} , "value" : { "count" : 1.0}}" 
} 

그래서 내 사용자 정의 시간 간격으로/계산 분당 문서를 집계,하지만.

이것에 대한 아이디어가 있으십니까?

답변

1

편집 : map reduce를 사용하는 나의 예가 효과적이지 않았지만, 이것이 대략하고 싶은 일이라고 생각합니다. 프로젝트를 사용하여 5 분 간격으로 반올림 한 타임 스탬프의 분을 포함하는 time 변수를 정의합니다. 정수 나누기는 쉽지만이 시간에는 mongodb 쿼리 언어가 지원하지 않는다고 생각하므로 대신 매분마다 minutes mod 5을 뺍니다. 그런 다음 이름과 시간 카운터로 그룹이 트릭을해야합니다.

query = [ 
    { 
     "$project": { 
      "_id":"$_id", 
      "name":"$name", 
      "time": { 
       "$subtract": [ 
        {"$minute":"$timestamp"}, 
        {"$mod": [{"$minute":"$timestamp"}, 5]} 
       ] 
      } 
     } 
    }, 
    { 
     "$group": {"_id": {"name": "$name", "time": "$time"}, "count":{"$sum":1}} 
    } 
] 
db.foo.aggregate(query) 
+0

감사합니다. 그러나 이것은 작동하지 않습니다. 30 분 (Math.floor (timestamp.getMinutes()/30)으로 접근하여 30 분 단위로 그룹화 할 수 있음을 의미하므로 14:25 PM과 14:35 PM의 문서는 두 번 계산됩니다. – user3169506

+0

I 내 의견을 편집했습니다. 비록 그것을 작동해야한다고 생각합니다 .25 div 30 = 0 괄호, 35 div 30 = 1 분 괄호에 14:35 분 문서에 가을 것이다. * Math.floor (timestamp.getMinutes()/30)'물론, 데이터 집합에 따라 시간, 일, 월, 년의 요소를 추가하는 것이 좋습니다. 그렇지 않으면 14:35 및 15:35가 종료됩니다. 같은 브래킷으로 묶음 – Mzzl

+1

시간 대신 임의의 시작점에서 30 분 단위로 집계 하시겠습니까? 그렇다면 14:35부터 15:05까지의 기간입니까? – Mzzl

관련 문제