MongoDB學習筆記——彙總

來源:互聯網
上載者:User

MongoDB學習筆記——彙總

最近要去的新項目使用mysql,趁著還沒忘記,總結記錄以下MongoDB的彙總。

彙總是泛指各種可以處理批量記錄並返回計算結果的操作。MongoDB提供了豐富的彙總操作,用於對資料集執行計算操作。在 mongod 執行個體上執行彙總操作可以大大簡化應用的代碼,並降低對資源的消耗。

在MongoDB中,像查詢之類的彙總操作都是使用 集合 中的文檔作為輸入,最終的結果會輸出一個或者多個文檔。

彙總管道

彙總管道是一個基於資料處理管道概念的架構。通過使用一個多階段的管道,將一組文檔轉換為最終的彙總結果。(aggregate詳細)

彙總管道是映射化簡的一個替代方案。而且對於彙總任務來說,彙總管道是一種優選的解決方案,因為映射化簡的複雜度可能無法保證。

彙總管道的每個步驟可以使用的記憶體最多是100MB。如果某個步驟超過了這個限制,MongoDB就會報錯了。如果需要處理大量資料,可以使用 allowDiskUse 這個選項,此時管道會把資料寫入臨時檔案。

有的管道階段可以使用管道運算式作為運算子。管道運算式可以對輸入文檔做指定的轉換。管道運算式使用一個文檔結構體,並且可以包含其他的運算式 。

管道運算式只可以操作當前管道中的文檔,不能訪問其他的文檔:運算式操作可以在記憶體中完成對文檔的轉換。

一般來說,運算式是無狀態的,並且僅在彙總過程中處於計算狀態,除了累計操作符運算式。

使用 $group 操作符的累計操作,需要在管道處理文檔的過程中維護自己的狀態(例如總數、最大值、最小值和相關資料)。

映射化簡

映射化簡是一種將大量資料轉換為有價值的*彙總*結果的資料處理方式。在MongoDB中,使用mapReduce 命令來執行映射化簡的操作。

請看下面的映射化簡操作:

在這個映射化簡操作中,MongoDB對每個輸入文檔(例如集合中滿足查詢條件的文檔)執行了*map*操作。映射操作輸出了索引值對結果。對那些有多個值的關鍵字,MongoDB執行*reduce*操作,收集並壓縮了最終的彙總結果。然後MongoDB把結果儲存到一個集合中。化簡函數還可以把結果輸出到*finalize*函數,進一步對彙總結果做處理,當然這步是可選的。

在MongoDB中,所有的映射化簡函數都是使用JavaScript編寫,並且運行在 mongod 進程中。映射化簡操作使用一個集合中文檔作為*輸入*,並且可以在映射階段之前執行任意的排序和限定操作。mapReduce 命令可以把結果作為一個文檔來返回,也可以把結果寫入集合。輸入集合和輸出集合可以是分區的。

如果選擇映射化簡操作即時返回結果,這些文檔一定要在 BSON文檔大小 限制以內,當前這個限制是16MB。

單一用途的彙總

彙總指的是一大類對資料集執行運算的方法,這些方法對輸入資料執行特定的步驟從而計算出一個結果。MongoDB提供了一組對資料集執行特定操作的彙總方法。

儘管與彙總管道和映射化簡比起來,它們的使用範圍有限,但是這些方法的名稱很直觀的表達了它的功能,非常易於理解使用。

1) 總數

MongoDB可以返回符合查詢條件的文檔總數。除了 count 命令, mongo 指令碼程式中的 count() 方法和 cursor.count() 方法都可以得到文檔總數。

例子

現在有一個名為 records 的集合中 只有 下面這些文檔:

{ a: 1, b: 0 }{ a: 1, b: 1 }{ a: 1, b: 4 }{ a: 2, b: 2 }

下面的操作會統計集合中的文檔個數,並最終返回數字 4:

db.records.count()

下面的操作會統計欄位 a 的值是 1 的文檔個數,最終返回 3:

db.records.count({a: 1})
2) 去除重複

去除重複 操作會返回查詢到的指定欄位值不重複的記錄。在 mongo 指令碼程式中,使用 distinct 命令或者 db.collection.distinct() 方法執行去重。請看下面的去除重複的例子:

例子

現在有一個名為 records 的集合中 只有 下面這些文檔:

{ a: 1, b: 0 }{ a: 1, b: 1 }{ a: 1, b: 1 }{ a: 1, b: 4 }{ a: 2, b: 2 }{ a: 2, b: 2 }

請看下面使用 db.collection.distinct() 方法對欄位 b 進行去除重複的操作:

db.records.distinct("b")

這個操作的結果是:

[ 0, 1, 4, 2 ]
3) 分組

分組 操作會把查詢到的文檔按照給定的欄位值進行分組。分組操作會返回一個文檔數組,其中的每個文檔包含了一組文檔的計算結果。

可以在 mongo 指令碼程式中通過 group 命令或者 db.collection.group() 方法來使用分組的功能。

group 命令不能在分區集合上運行。特別需要注意一點, group 操作的結果集大小不能超過16MB。

例子

現在有一個名為 records 的集合,它包含有如下文檔:

{ a: 1, count: 4 }{ a: 1, count: 2 }{ a: 1, count: 4 }{ a: 2, count: 3 }{ a: 2, count: 1 }{ a: 1, count: 5 }{ a: 4, count: 4 }

請考慮用 group 命令對集合中的文檔進行分組,分組條件是欄位 a 值小於 3 ,同時需要對每組的count 欄位計數:

db.records.group({   key: {a: 1},   cond: {a: {$lt: 3}},   reduce: function(cur, result) { result.count += cur.count },   initial: {count: 0}})

這次分組操作的結果是:

[  {a: 1, count: 15},  {a: 2, count: 4}] 

更多MongoDB相關內容可以看看以下的有用連結: 

MongoDB 3.0 正式版發布下載 

CentOS編譯安裝MongoDB

CentOS 編譯安裝 MongoDB與mongoDB的php擴充

CentOS 6 使用 yum 安裝MongoDB及伺服器端配置

Ubuntu 13.04下安裝MongoDB2.4.3

MongoDB入門必讀(概念與實戰並重)

Ubunu 14.04下MongoDB的安裝指南

《MongoDB 權威指南》(MongoDB: The Definitive Guide)英文文字版[PDF]

Nagios監控MongoDB分區叢集服務實戰

基於CentOS 6.5作業系統搭建MongoDB服務

MongoDB 的詳細介紹:請點這裡
MongoDB 的:請點這裡

本文永久更新連結地址:

相關文章

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.