MongoDB學習筆記(一)

来源:http://www.cnblogs.com/zt110e5/archive/2017/05/21/6885746.html
-Advertisement-
Play Games

1.MongoDB簡介 MongoDB介紹 MongoDB是面向文檔的非關係型資料庫,不是現在使用最普遍的關係型資料庫,其放棄關係模型的原因就是為了獲得更加方便的擴展、穩定容錯等特性。面向文檔的基本思路就是:將關係模型中的“行”的概念換成“文檔(document)”模型。面向文檔的模型可以將文檔和數 ...


1.MongoDB簡介

 

MongoDB介紹

MongoDB是面向文檔的非關係型資料庫,不是現在使用最普遍的關係型資料庫,其放棄關係模型的原因就是為了獲得更加方便的擴展、穩定容錯等特性。面向文檔的基本思路就是:將關係模型中的“行”的概念換成“文檔(document)”模型。面向文檔的模型可以將文檔和數組內嵌到文檔中。因此,實際中可以用一條數據表示非常複雜的結構。
MongoDB沒有預定義模式:文檔的鍵(key)和值(value)不再是固定的類型和大小,而且根據需求要添加或者刪除欄位變得更容易了。由於沒有模式需要更改,通常不需要遷移大量數據。不必將所有數據都放到一個模子裡面,應用層可以處理新增或丟失的鍵。這樣開發者可以非常容易地變更數據模型。
實際應用中,隨著數據量的增大,資料庫都要進行擴展。擴展有縱向擴展和橫向擴展。縱向擴展是使用計算能力更強的機器,也是最省力的方法,但是很容易達到物理極限,無論花多少錢也買不到最新的機器了。橫向擴展就是通過分區將數據分散到更多的機器上。MongoDB的設計採用橫向擴展。面向文檔的數據模型使它很容易地在多台伺服器之間進行數據分割。還可以自動處理跨集群的數據和負載,自動重新分配文檔,以及將用戶請求路由到正確的機器上。開發者根本不用考慮資料庫層次的擴展問題,需要擴展資料庫時,在集群中添加機器即可,MongoDB會自動處理後續的事情。
MongoDB有如上各種特性,但為了達到這些,他也放棄了關係型資料庫的某些功能如表連接join和複雜的多行事務。

2017-05-12_214955.png-8kB 
直觀瞭解: 
2017-05-17_165633.png-13kB

 

MongoDB的優勢與劣勢

 

優勢

  1. 快速!基於記憶體,將熱數據存放在物理記憶體中(不僅僅只是索引和少部分數據),從而提高了整體速度和效率。
  2. 高擴展性!MongoDB的高可用和集群架構擁有十分高的擴展性。
  3. 自身的FailOver機制!在副本集中,當主庫遇到問題,無法繼續提供服務的時候,副本集將選舉一個新的主庫繼續提供服務。
  4. JSon格式的數據!MongoDB的Bson和JSon格式的數據十分適合文檔格式的存儲與查詢。
 

劣勢

  1. 應用經驗少!由於NoSQL興起時間短,應用經驗相比關係型資料庫較少。
  2. 由於以往用到的都是關係型資料庫,可能會造成使用者一開始的不適應。
  3. 無事務機制!MongoDB本身沒有自帶事務機制,若需要在MongoDB中實現事務機制,需通過一個額外的表,從邏輯上自行實現事務。

 

2.MongoDB與MYSQL對比

資料庫MongoDBMySQL
資料庫模型 非關係型 關係型
存儲方式 以類JSON的文檔的格式存儲 不同引擎有不同的存儲方式
查詢語句 MongoDB查詢方式(類似JavaScript的函數) SQL語句
數據處理方式 基於記憶體,將熱數據存放在物理記憶體中,從而達到高速讀寫 不同引擎有自己的特點
成熟度 新興資料庫,成熟度較低 成熟度高
廣泛度 NoSQL資料庫中,比較完善且開源,使用人數在不斷增長 開源資料庫,市場份額不斷增長
事務性 僅支持單文檔事務操作,弱一致性 支持事務操作
占用空間 占用空間大 占用空間小
join操作 MongoDB沒有join MySQL支持join

下麵是Mongodb與Mysql的操作命令的對比: 
2017-05-05_102256.png-15kB


 

MongoDB基礎知識與CRUD

1.文檔(document):相當於傳統關係型資料庫的“行”,但比傳統行表示的信息更加複雜。例如:

 
{"name":"jack","age":18,"sex":"male"}

2.集合(collection):這個在MongoDB中代表一組文檔,類似於關係型資料庫中的表。但在MongoDB中的表(就是集合)是沒有模式的,你可以將完全不同的文檔放入同一個集合中.但在實際使用中,為特定集合隱性規定一種模式。註:當集合里沒有任何文檔時集合其實也是不存在的。當第一個文檔插入時,集合就會被創建。 
3.資料庫(database):在MongoDB中,一組集合可以組成一個資料庫。一個MongoDB實例可以承載多個資料庫。每個資料庫都有獨立的許可權控制。在實際應用中,通常,一個應用的所有數據放置在一個資料庫中。 
4.數據類型:MongoDB中的文檔類似於JSON。JSON是一種簡單的數據交換格式,在數據類型方面,只支持:null,布爾,數字,字元串,數組和對象。這幾種類型在某些實際應用中表現力還是不夠,比如JSON本身不直接支持日期類型,對於數字,JSON本身也沒法區分整數和浮點數,更不能區分32位數字和64位數字。為此,MongoDB再保留了JSON的各類特性外,又為其添加了一些數據類型。 
1.null:用於表示空值或不存在的欄位。Shell中這樣表示:{"x":null} 
2.布爾:有兩個值,true和false。Shell中這樣使用:{"x":true} 
3.數字:Shell中數字均為64位浮點數,如在Shell中{"x":3.14}{"x":3}這兩個文檔中的值均是64位的浮點數。 
4.字元串:這個用的最廣,Shell中這樣表示:{"x":"hello world!"} 
5.日期:這個在數據存儲時,存儲的是從標準紀元開始的毫秒數,沒有存儲時區信息。 
6.正則表達式:文檔中可以包含正則表達式,採用JavaScript的正則表達式語法即可,Shell中這樣表示:{"x":/foobar/i}
7.數組:數組是一組值,既可以表示為有序對象(列表,棧,隊列等)也可以表示無序對象(集合),Shell中這樣表示一個數組:{"things":["pie",3.14]}。 
8.內嵌文檔:把一個文檔整個作為另一個文檔某一個鍵對應的值。 
其他包括二進位數據,代碼等。

 

MongoDB入門(Shell基本操作)

運行mongo啟動shell: 
2017-05-05_154321.png-3.8kB 
shell是一個功能完備的JavaScript解釋器,可運行任意的JavaScript程式。這裡不做示例。 
MongoDB的預設資料庫為"db",該資料庫存儲在data目錄中。 
1.選擇資料庫

#選擇名test資料庫
use tset

  

2017-05-05_154819.png-1.6kB 
如果忘記了資料庫名稱可以輸入如下代碼查詢所有資料庫名稱:"show dbs" 命令可以顯示所有數據的列表

 
show dbs

  

2017-05-05_154952.png-2.7kB 
查看資料庫中的集合名:

 
show collections

  

結果如圖所示: 
2017-05-05_161235.png-2kB 
下表列出了 RDBMS 與 MongoDB 對應的術語: 
2017-05-17_170031.png-4.5kB

 

插入文檔

insert函數可將一個文檔插入到集合中去。以一個博客舉例。先創建一個叫post的變數(JavaScript對象)有三個鍵和對應的屬性。插入代碼:

 
db.blog.insert(post)

如圖所示: 
2017-05-05_161551.png-6kB 
批量插入

 
db.blog.insertMany([{"_id":0},{"_id":1},{"_id":2}])

  

2017-05-05_171812.png-3.5kB

 

查詢文檔

查詢代碼如下:

 
db.blog.find()

如圖所示: 
2017-05-05_161943.png-5kB 
多出來的"_id"就是MongoDB自動創建的預設為ObjectID類型的對象。在一個集合里,每個文檔都由唯一的"_id",確保集合中的每個文檔都能被唯一標識,它採用12位元組的存儲空間,由24個16進位數字組成,可分為四部分組成:

{0,1,2,3}{4,5,6}{7,8}{9,10,11}
時間戳 機器碼 PID(線程碼) 自增計數器

如果插入文檔時沒有"_id"鍵,系統會為我們自動創建一個。 
若只想查看一個文檔,可以用findOne:

db.blog.findOne()

  

查詢具體的某一個文檔那麼就要以json的形式添加查詢條件,例如:

 
db.blog.find({"title":"My Blog Post"})

  

以上實例中類似於 WHERE 語句:WHERE title = 'My Blog Post';

2017-05-05_162233.png-7.7kB

 

修改文檔

如果給博客新增一個評論功能,則需要新增key-value,用於保存評論數組。

 
post.comments = []

之後用新版本的文檔替換舊版本:

 
db.blog.update({"title":"My Blog Post"},post)

2017-05-05_162757.png-7.3kB

使用修改器:

"$Set":用來指定一個欄位的值,若欄位不存在,則創建它。
db.users.update({"sex":"male"},{"$Set":{"gift":"happy birthday!"}})
/*這樣只會更新一個文檔,若要更新多個文檔,則需要將update的第四個參數設置為true*/
db.users.update({"sex":"male"},{"$Set":{"gift":"happy birthday!"}},false,true) 
"$inc":用來增加已有鍵的值,若鍵不存在,就創建它。(與"$Set"類似,專門用來增加數字的,只能用於整形,長整型,雙精度浮點型)
db.games.update({"game":"pinball","user":"joe"},{"$inc":{"score":50}}) 
"$push":會向已有的數組末尾加入一個元素,若數組不存在,則創建數組。與"$each"自操作符一同使用可以一次添加多個值。
db.stock.ticker.update({"_id":"1"},{"$push":{"hourly":{"$each":[562.667,562.790,562.123]}}}) 
"$addToSet":可以避免重覆插入。若數組內已有相同數據,則不差入。與"$each"自操作符一同使用可以一次添加多個值。
db.users.update({"_id""1},{"$addToSet":{"emails":"[email protected]"}})
"$push":刪除數組裡的元素.("$pop":將數組看成隊列或棧,從兩端刪除。"$pull":將所匹配到的數組中的值刪除,而不是只刪除一個)

刪除文檔

db.blog.remove({"title":"My Blog Post"})

2017-05-05_162941.png-2.9kB 
刪除整個集合用drop()

 
db.blog.drop()

索引

MongoDB使用 ensureIndex() 方法來創建索引。

db.COLLECTION_NAME.ensureIndex({KEY:1})

語法中 Key 值為你要創建的索引欄位,1為指定按升序創建索引,如果你想按降序來創建索引指定為-1即可。 
當然也可以給多個欄位建立索引

db.col.ensureIndex({"title":1,"description":-1})

管道聚合

MongoDB的聚合管道將MongoDB文檔在一個管道處理完畢後將結果傳遞給下一個管道處理。管道操作是可以重覆的。 
表達式:處理輸入文檔並輸出。表達式是無狀態的,只能用於計算當前聚合管道的文檔,不能處理其它的文檔。 
這裡我們介紹一下聚合框架中常用的幾個操作:

  • $project:修改輸入文檔的結構。可以用來重命名、增加或刪除域,也可以用於創建計算結果以及嵌套文檔。
 
db.article.aggregate(
{ $project : {
title : 1 ,
author : 1 ,
}}
);
  • $match:用於過濾數據,只輸出符合條件的文檔。
db.articles.aggregate( [
{ $match : { score : { $gt : 70, $lte : 90 } } },
{ $group: { _id: null, count: { $sum: 1 } } }
] );
  • $limit:用來限制MongoDB聚合管道返回的文檔數。
db.article.find().limit
  • $skip:在聚合管道中跳過指定數量的文檔,並返回餘下的文檔。
db.article.aggregate( { $skip : 5 });
  • $group:將集合中的文檔分組,可用於統計結果。

  • $sort:將輸入文檔排序後輸出。


 

Java操作MongoDB

 

連接資料庫

連接資料庫,你需要指定資料庫名稱,如果指定的資料庫不存在,mongo會自動創建資料庫。 
所需jar包: mongo-java-driver-3.2.2.jar 
連接資料庫的Java代碼如下:

 1 import com.mongodb.MongoClient;
 2 import com.mongodb.client.MongoDatabase;
 3 public class MongoDBJDBC{
 4 public static void main( String args[] ){
 5 try{
 6 // 連接到 mongodb 服務
 7 MongoClient mongoClient = new MongoClient( "localhost" , 27017 );
 8 // 連接到資料庫
 9 MongoDatabase mongoDatabase = mongoClient.getDatabase("test");
10 System.out.println("Connect to database successfully");
11 }catch(Exception e){
12 System.err.println( e.getClass().getName() + ": " + e.getMessage() );
13 }
14 }
15 }

 

創建集合: 
我們可以使用 com.mongodb.client.MongoDatabase 類中的createCollection()來創建集合 
代碼片段如下:

 
import com.mongodb.MongoClient;
import com.mongodb.client.MongoDatabase;
public class MongoDBJDBC{
public static void main( String args[] ){
try{
// 連接到 mongodb 服務
MongoClient mongoClient = new MongoClient( "localhost" , 27017 );
// 連接到資料庫
MongoDatabase mongoDatabase = mongoClient.getDatabase("test");
System.out.println("Connect to database successfully");
mongoDatabase.createCollection("test");
System.out.println("集合創建成功");
}catch(Exception e){
System.err.println( e.getClass().getName() + ": " + e.getMessage() );
}
}
}

 

 

插入文檔

 
//插入文檔
/**
* 1. 創建文檔 org.bson.Document 參數為key-value的格式
* 2. 創建文檔集合List<Document>
* 3. 將文檔集合插入資料庫集合中 mongoCollection.insertMany(List<Document>) 插入單個文檔可以用 mongoCollection.insertOne(Document)
* */
Document document = new Document("title", "MongoDB").
append("description", "database").
append("likes", 100).
append("by", "Fly");
List<Document> documents = new ArrayList<Document>();
documents.add(document);
collection.insertMany(documents);
System.out.println("文檔插入成功");

 

 

查詢文檔

 
//檢索所有文檔
/**
* 1. 獲取迭代器FindIterable<Document>
* 2. 獲取游標MongoCursor<Document>
* 3. 通過游標遍歷檢索出的文檔集合
* */
FindIterable<Document> findIterable = collection.find();
MongoCursor<Document> mongoCursor = findIterable.iterator();
while(mongoCursor.hasNext()){
System.out.println(mongoCursor.next());
}

 

 

修改文檔

 
//更新文檔 將文檔中likes=100的文檔修改為likes=200
collection.updateMany(Filters.eq("likes", 100), new Document("$set",new Document("likes",200)));
//檢索查看結果
FindIterable<Document> findIterable = collection.find();
MongoCursor<Document> mongoCursor = findIterable.iterator();
while(mongoCursor.hasNext()){
System.out.println(mongoCursor.next());
}

 

 

刪除文檔

 
//刪除符合條件的第一個文檔
collection.deleteOne(Filters.eq("likes", 200));
//刪除所有符合條件的文檔
collection.deleteMany (Filters.eq("likes", 200));
//檢索查看結果
FindIterable<Document> findIterable = collection.find();
MongoCursor<Document> mongoCursor = findIterable.iterator();
while(mongoCursor.hasNext()){
System.out.println(mongoCursor.next());
}

 

   
您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 現在市場是的手機尺寸一般都是小於6寸的,而平板一般是大於6寸的,所以可以通過計算設備的尺寸來判斷設備是平板還是手機。 判斷代碼如下: ...
  • 將別人的項目導入自己的環境下出現的問題。 Gradle refresh failed; Error:Cannot locate factory for objects of type DefaultGradleConnector, as ConnectorServiceRegistry 解決方法,清 ...
  • 當cheeckout從svn上update時,由於某個xib存在衝突,所以便在 sourec Code 中解決衝突之後想在xib中直接查看,便提示以上錯誤,依據錯誤提示是由於指向的xib文件內容存在問題,所以需要重新指定其xib文件才行。 選中上圖紅框的部分重新在項目的路徑下選中該文件即可。 ...
  • 將高度拉伸了 ...
  • Vysor Pro破解助手(Vysor Crack Assistant),支持V1.6.6到V1.7.7之間的版本。 ...
  • 背景描述 重裝的Mac系統,一切開發相關的配置從零開始。 描述文件 初始狀態 從開發者賬號上下載開發所需要的描述文件之後,提示如下 它提示4個要點的信息缺少了2個,點擊紅框部分,提示如下 它提示現在使用的描述文件中的證書是缺乏與其相對的私鑰的,私鑰是從當前設備製作的,之後還需要上傳到開發者賬號進行重 ...
  • 在String.xml中添加: ...
  • 一直以來,做 Java web 開發都是用 eclipse , 可是到 eclipse 官網一看,我的天 http://www.eclipse.org/downloads/eclipse-packages/ 那麼多應該下載哪一個?這是一個問題? 其實 eclipse 為每一種開發者,都提供了不同的版 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...