(原)MongoDB在系統中的使用


序)Nosql並不是要取代原有的數據產品,而是為不同的應用場景提供更多的選擇。

 

一)結構類型

  傳統數據庫的領域在於結構化文檔,對於非結構化文檔和半結構化文檔,它能處理,但是有一定的缺陷,那么什么又是結構化文檔,概括如下:

  結構化信息——這種信息可以在關系數據庫中找到,多年來一直主導着IT應用。這是關鍵任務OLTP系統業務所依賴的信息,另外,還可對結構數據庫信息進行排序和查詢;

  半結構化信息——這是IT的第二次浪潮,包括電子郵件,文字處理文件以及大量保存和發布在網絡上的信息。半結構化信息是以內容為基礎,可以用於搜索,這也是谷歌存在的理由;

  非結構化信息——該信息在本質形式上可認為主要是位映射數據。數據必須處於一種可感知的形式中(諸如可在音頻、視頻和多媒體文件中被聽或被看)。許多大數據都是非結構化的,其龐大規模和復雜性需要高級分析工具來創建或利用一種更易於人們感知和交互的結構。

 

二)MongoDB和行導向數據庫的區別

  老實說,我覺得Nosql領域比較奇葩的東西算是Hive,不過在此不介紹它,對於項目中使用到MongoDB,也是有一定原因的,我一直以為Nosql這種東西和行導向數據庫並不沖突,它僅僅是行導向數據的一個補充,對於MongoDB,它和我們用的mysql,Oracle等有什么區別,曾經我也查找過一些東西,發現網上很多相關的文章都是千篇一律,幾乎一模一樣,沒啥價值,於是捉摸自己總結下。

  舉個栗子:

uid name age
1 張三 18

 

 

  在上面的表中,很直接,數據也很直觀,但是如果我們需要存儲另外一個東西:頭像,一般人會這樣干:

uid name age photo
1 張三 18 ./upload/1.png

 

 

  盡管不同數據庫都提供了直接存儲二進制的數據庫字段,但是我還是會選擇以上的存儲方式,我相信也有很多人也會這樣做,這樣做其實沒有什么不好,但是如果我們的文件很大,幾個GB,那么無論讀還是寫都會很耗時,成為系統的瓶頸,基於這種情況,才會誕生雲計算以及Nosql這些東西,也就是說Hadoop,Hbase等誕生的原因是:

  多年來磁盤存儲容量快速增加的同時,訪問速度-磁盤數據讀取速度卻未能與時俱進,尋址時間的提高遠遠慢於傳輸速率的提高,尋址是將磁盤移動到特定磁盤位置進行讀寫操作,它是導致磁盤操作延遲的主要原因,而傳輸速率取決與磁盤的帶寬。

  於是人們想出了一個辦法:既然在一個服務器讀取一個文件需要100個小時,那么將文件放在100個服務器,每個服務器放1%的數據,那么1小時就搞定了,這也是Hadoop的核心思想,MongoDB數據庫繼承了這一思想,它的區塊划分,以及節點分裂,都延續了這樣的思想,另一方面,MongoDB又吸取了memcached的東西,提前申請一片內存區域以及文件區域,將內存中的地址和物理地址對應起來,可以極高的提高速度,這也是MongoDB相當的消耗內存和磁盤的原因之一。

  

三)MongoDB應用范圍

  1:MongoDB與傳統數據庫整合:

id user_id title content time
1 張三 文章標題 文章內容 時間

 

 

  在以上表中,如果內容是一個包含上千上萬字的文章,一般會該字段的內容丟入MongoDB,然后在此放入MongoDB的ID。

  2:MongoDB取代傳統數據庫:

  在某些事物要求不高的場合,以及允許出現部分錯誤的系統中,可以使用MongoDB取代傳統數據庫,例如論壇,博客等系統,舉個栗子:

  博客有人發表了一篇文章,MongoDB存儲如下:

  

> db.article.insert({"title":"測試文章","content":"測試內容", "time":"17822455", "uid":"1"});
WriteResult({ "nInserted" : 1 })
> db.article.findOne();
{
        "_id" : ObjectId("546168c9573c0742d8be1544"),
        "title" : "測試文章",
        "content" : "測試內容",
        "time" : "17822455",
        "uid" : "1"
}
> 

  現在有一個人對這篇文章進行了評論,如下:

  

> var articleInfo = db.article.findOne({"_id":ObjectId("54616db1d92589121def0c70")});
> articleInfo;
{
        "_id" : ObjectId("54616db1d92589121def0c70"),
        "title" : "測試文章",
        "content" : "測試內容",
        "time" : "17822455",
        "uid" : "1"
}
> articleInfo.commentary={"uid":"2",info :{"content":"這篇文章不錯","times":"145881444"}};
{
        "uid" : "2",
        "info" : {
                "content" : "這篇文章不錯",
                "times" : "145881444"
        }
}
> db.article.update({"_id": ObjectId("54616db1d92589121def0c70")},articleInfo);
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
> db.article.findOne({"_id":ObjectId("54616db1d92589121def0c70")});
{
        "_id" : ObjectId("54616db1d92589121def0c70"),
        "title" : "測試文章",
        "content" : "測試內容",
        "time" : "17822455",
        "uid" : "1",
        "commentary" : {
                "uid" : "2",
                "info" : {
                        "content" : "這篇文章不錯",
                        "times" : "145881444"
                }
        }
}
> 

 

  現在又有一個人對它評論如下:

  於是MongoDB的存儲結構成了這樣:

  

> db.article.update({"_id":ObjectId("54617115d92589121def0c72")}, {"$push": {"commentary":{"uid":3,info :{"content":"我也這篇文章不錯","times":"1444"}}}});
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
> db.article.findOne({"_id":ObjectId("54617115d92589121def0c72")});
{
        "_id" : ObjectId("54617115d92589121def0c72"),
        "title" : "測試文章",
        "content" : "測試內容",
        "time" : "17822455",
        "uid" : "1",
        "commentary" : [
                {
                        "uid" : 2,
                        "info" : {
                                "content" : "這篇文章不錯",
                                "times" : "1444"
                        }
                },
                {
                        "uid" : 3,
                        "info" : {
                                "content" : "我也這篇文章不錯",
                                "times" : "1444"
                        }
                }
        ]
}
> 

  由此可見,如果再有評論,繼續往后加就OK,MongoDB對此的存儲是一目了然,伸縮性很強,如果不能夠在代碼中實現對數據一致性的處理,那么還是使用回關系型數據庫為妙,在這種事務性不太強的場合,使用MongoDB是可以取代掉關系型數據庫的。

四)MongoDB使用

  由於之前使用logback處理日志,自己還得寫一大堆的shell腳本,各種awk處理文本分析用戶行為丟入postgres,可能自己技術不到家,但是自己能夠想出的東西也就這些,於是在這個項目中毅然決定用MongoDB作為日志分析系統。如果不在分布式中,使用Nosql沒有價值,碼字太辛苦了。。

  

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM