成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

Mongodb體系結(jié)構(gòu)與客戶端基本操作及注意細節(jié)

數(shù)據(jù)庫 其他數(shù)據(jù)庫 MongoDB
說到Mongodb的體系結(jié)構(gòu),免不了與關(guān)系型數(shù)據(jù)庫做個對比。本文以MySQL為例來進行一些比較。

[[128855]]

說到Mongodb的體系結(jié)構(gòu),免不了與關(guān)系型數(shù)據(jù)庫做個對比。這里以MySQL為例,我們進行一些比較:

從邏輯結(jié)構(gòu)上對比:

MySQL層次概念             MongoDB層次概念

數(shù)據(jù)庫(database)      數(shù)據(jù)庫(database)

表(table)                     集合(collection)

記錄(row)                    文檔(document)

在MongoDB中沒有行、列、關(guān)系的概念,集合中的文檔相當于一條記錄,這體現(xiàn)了模式自由的特點。

從數(shù)據(jù)存儲結(jié)構(gòu)上對比:

MySQL的每個數(shù)據(jù)庫存放在一個與數(shù)據(jù)庫同名的文件夾中,MySQL如果使用MyISAM存儲引擎,數(shù)據(jù)庫文件類型就包括.frm、.MYD(存放數(shù)據(jù),D為Data)、.MYI(存放索引,I為Index)。

MongoDB的默認數(shù)據(jù)目錄時/data/db,它負責存儲所有MongoDB的數(shù)據(jù)文件。在MongoDB內(nèi)部,每個數(shù)據(jù)庫都包含一個.ns文件和一些數(shù)據(jù)文件,而且這些數(shù)據(jù)文件會隨著數(shù)據(jù)量的增加而變得越來越多,例如系統(tǒng)中有一個叫mydb的數(shù)據(jù)庫,那么構(gòu)成mydb這個數(shù)據(jù)庫的文件就會有mydb.ns,mydb.0,mydb.1等等組成。

mydb.ns記錄了數(shù)據(jù)庫Json對象的命名空間(ns時namespace的縮寫),也就是數(shù)據(jù)庫集合里面的命名空間。mydb.0和mydb.1是存放數(shù)據(jù)庫mydb的對象的空間,且大小按照2的n次方大小遞增。如mydb.`0的大小是16M,當數(shù)據(jù)庫mydb存滿16M之后,就會形成生成mydb.1繼續(xù)存儲,mydb.1的大小為32M,以此類推,隨著數(shù)據(jù)的增加,還會有mydb.2、mydb.3等文件出現(xiàn),大小64M、128M。默認情況下,現(xiàn)在版本的Mongodb在數(shù)據(jù)庫剛剛建立時就會預(yù)先分配好XXX.0和XXX.1共48M空間,之后再隨著插入對象的增多而生成后續(xù)xxx.2等。

MongoDB客戶段基本操作:

首先當然是要確認MongoDB的mongod服務(wù)是打開的。詳細見我之前的博客。

打開MongoDB客戶端的方法時運行MongoDB的bin目錄下的mongo。

  1. [neil@neilhost Downloads]$ pstree -p | grep mongod 
  2. |-mongod(3556)-+-{mongod}(3557
  3. | |-{mongod}(3558
  4. | |-{mongod}(3559
  5. | |-{mongod}(3563
  6. | |-{mongod}(3564
  7. | |-{mongod}(3565
  8. | |-{mongod}(3566
  9. | |-{mongod}(3567
  10. | `-{mongod}(3568
  11. [neil@neilhost Downloads]$ cd /usr/local/mongodb/bin/mongo 
  12. bash: cd: /usr/local/mongodb/bin/mongo: 不是目錄 
  13. [neil@neilhost Downloads]$ sudo /usr/local/mongodb/bin/mongo 
  14. MongoDB shell version: 2.6.8 
  15. connecting to: test 
  16. Welcome to the MongoDB shell. 
  17. For interactive help, type "help"
  18. For more comprehensive documentation, see 
  19. http://docs.mongodb.org/ 
  20. Questions? Try the support group 
  21. http://groups.google.com/group/mongodb-user 

接下來介紹幾個基本操作,以及一個細節(jié)。

show dbs的意思是顯示mongodb中所有的數(shù)據(jù)庫。剛安裝好mongodb時,默認有兩個數(shù)據(jù)庫admin和local,不去管他們。

db指的是當前工作環(huán)境所在的數(shù)據(jù)庫。當你每次進入mongo時。默認進入的數(shù)據(jù)庫時test,它是一個隱式存儲的數(shù)據(jù)庫,如果需要進入特定的數(shù)據(jù)庫,或是想建立一個新的數(shù)據(jù)庫,只需要“use 數(shù)據(jù)庫名稱”就可以了。在mongodb中不需要create database這種操作,想用就用,mongodb會自動幫我們建立了數(shù)據(jù)庫,就像一個服務(wù)周到的“黑執(zhí)事”。這里,我use dt2建立了一個新的數(shù)據(jù)庫dt2,客戶端立即現(xiàn)實工作環(huán)境轉(zhuǎn)入到dt2。但是,如果你show dbs,發(fā)現(xiàn)數(shù)據(jù)庫并沒有真正建立。是需要新建表并且插入一些數(shù)據(jù)才可以嗎?不是,只需要你在當前數(shù)據(jù)庫dt2輸入任何一個細小的操作命令,如顯示當前數(shù)據(jù)庫的集合有哪些,這時候dt2就會被真正建立了。

  1. connecting to: test 
  2. > show dbs 
  3. admin (empty) 
  4. dt1 0.078GB 
  5. local 0.078GB 
  6. > db 
  7. test 
  8. > use dt2 
  9. switched to db dt2 
  10. > show dbs 
  11. admin (empty) 
  12. dt1 0.078GB 
  13. local 0.078GB 
  14. > show collections 
  15. > show dbs 
  16. admin (empty) 
  17. dt1 0.078GB 
  18. dt2 (empty) 
  19. local 0.078GB 

在上面的命令中,show collections是顯示當前數(shù)據(jù)庫下的集合有哪些。因為現(xiàn)在還沒有集合,所以什么都不顯示。

接下來我們嘗試建立集合和插入數(shù)據(jù)。

  1. > db.student.find() 
  2. > show collections 

mongodb建立集合(表),依然是一個不需要聲明著建立表的過程。即不需要create collection或create table之類操作。

直接用即可。

這里我們依舊首先驗證一個小細節(jié)。什么樣子的表操作才會導(dǎo)致表的生成。通過上面的命令。我們在還沒有student集合的時候?qū)ζ溥M行查詢(find()),但是,之后顯示集合的命令可以看到并沒有為dt2建立student集合。

于是我直接在student表中插入一個Json對象(存儲在Mongodb的單元是Bson對象,在邏輯概念上是一個文檔)

  1. > db.student.insert({name:"Viper",age:20}) 
  2. WriteResult({ "nInserted" : 1 }) 
  3. > show collections 
  4. student 
  5. system.indexes 

這時候,當show collections的時候可以看見,student集合已經(jīng)有了。這說明在建立集合時,必須想新的集合中插入有效數(shù)據(jù),才能真正建立集合。

總結(jié)上面的兩個細節(jié)就是,在MongoDB中建立數(shù)據(jù)庫時,只要use數(shù)據(jù)庫,并且在數(shù)據(jù)庫下執(zhí)行任何看似不會有任何影響的命令,如查詢集合,都會使得數(shù)據(jù)庫建立起來;但是,如果在數(shù)據(jù)庫下,對于新建集合的文檔查詢是不會導(dǎo)致集合建立的,必須有文檔數(shù)據(jù)插入集合,才能使得集合真正建立起來。這樣一對細節(jié)很多人未必知道!

另外當空數(shù)據(jù)庫建立集合時,會生成一個索引表,system.indexes。該數(shù)據(jù)庫下的所有集合的ObjectId的索引值全都存放在這里面。

#p#

那么下面我們來分別說說增刪改查。

前面的例子中其實已經(jīng)加入了一條文檔,這里我們在增加一個文檔到student集合。

  1. > db.student.insert({name:"TA",age:18,phone:["1311234567","021-87658765"],GPA:{Math:88,English:99}}) 
  2. WriteResult({ "nInserted" : 1 }) 
  3. > db.student.find() 
  4. "_id" : ObjectId("54fb0d853fc8173ba3302e6c"), "name" : "Viper""age" : 20 } 
  5. "_id" : ObjectId("54fb10493fc8173ba3302e6d"), "name" : "TA""age" : 18"phone" : [ "1311234567""021-87658765" ], "GPA" : { "Math" : 88"English" : 99 } } 

這里可以看到,我向mongodb的student集合中插入的兩個文檔,它們的“表結(jié)構(gòu)”是不一樣的。這就是NoSQL數(shù)據(jù)庫與關(guān)系型數(shù)據(jù)庫的最重要區(qū)別之一(其他區(qū)別之前也提過,ACID特性(事務(wù)的支持),并發(fā))。

其中第二條文檔中我們看到key-value的value可以是一些數(shù)、字符串等基本類型外,還可以是數(shù)組(其實可以理解為棧,后面的博客文章會介紹value是數(shù)組情況下的push和pop,所以理解為一種類似于棧的列表更妥貼),如上面的phone鍵。更強大的地方是,文檔,即插入的Json對象的keybalue的value可以是另一個Json對象,如上面的GPA鍵。

其實,這些數(shù)組、json對象更像是python語法中的列表和字典,哈哈哈哈。。。

這里,我將key-value的value數(shù)據(jù)類型做個整理:

  • null: 表示空值或者不存在的值
  • 布爾類型: true和false,如{male:true}
  • 32位整數(shù): Mongodb的控制臺使用JS引擎進行輸入,而JS僅僅支持64位浮點數(shù),所以32位整數(shù)會被自動轉(zhuǎn)義
  • 64位整數(shù): 同上,會被自動轉(zhuǎn)義成64位浮點數(shù)
  • 64位浮點數(shù): Mongodb的控制臺數(shù)字的默認類型。如{salary:23871.12}
  • 字符串 :UTF-8字符串都可以表示為字符串類型的數(shù)據(jù)
  • 符號: 在MongoDB中不支持這種類型,將自動轉(zhuǎn)義成字符串
  • ObjectId: MongoDB獨有,對象id時文檔中***的12位16進制的id。(時間戳 | 機器 | PID | 計數(shù)器)
  • 日期: 注意:使用的時候要加上new。如{birthday:new Date()}
  • 正則表達式: 文檔鍵值可以包含正則表達式,其正則表達式采用JS語法來表示。如:{key:/ho/i}
  • 代碼: 文檔中可以包含JS文檔。如{key:function(){/*........*/}}(可以是沒有函數(shù)名的匿名函數(shù))
  • 數(shù)組:文檔中的key的value可以表示為數(shù)組,數(shù)組內(nèi)還可以嵌套數(shù)組。
  • 內(nèi)嵌文檔: 文檔可以包含別的文檔,也可以作為value嵌入到父文檔中。如{x:{name:"happyBKs",age:2}}

插入之后的Json對象我們可以看到,新插入的每個文檔都被賦予了一個_id,這是可以理解為記錄的主,是mongodb自動生存成的key,它的value是一個特定的ObjectId對象,是一個96位二進制數(shù),由機器碼、機器進程號、時間、當前命名空間的編號四個部分自動生成,***。當然,如果你愿意,也可以在插入Json對象時自己指定_id的value,只要未發(fā)生主鍵沖突,都可以正常插入。

增加一個記錄除了用insert方法之外還有一種方法,那就是save。它的功能是當你指定Json的_id,并且_id在集合中已經(jīng)存在,那么它會更新相應(yīng)的文檔;否則,則插入一個新的文檔。請看下面這個例子,_id的為1的Json對象,***次save是被添加,而第二次則是被更改。

  1. > db.student.find() 
  2. "_id" : ObjectId("54fb0d853fc8173ba3302e6c"), "name" : "Viper""age" : 20 } 
  3. "_id" : ObjectId("54fb10493fc8173ba3302e6d"), "name" : "TA""age" : 18"phone" : [ "1311234567""021-87658765" ], "GPA" : { "Math" : 88"English" : 99 } } 
  4. > db.student.save({_id:1,name:"happyBKs",age:0}) 
  5. WriteResult({ "nMatched" : 0"nUpserted" : 1"nModified" : 0"_id" : 1 }) 
  6. > db.student.find() 
  7. "_id" : ObjectId("54fb0d853fc8173ba3302e6c"), "name" : "Viper""age" : 20 } 
  8. "_id" : ObjectId("54fb10493fc8173ba3302e6d"), "name" : "TA""age" : 18"phone" : [ "1311234567""021-87658765" ], "GPA" : { "Math" : 88"English" : 99 } } 
  9. "_id" : 1"name" : "happyBKs""age" : 0 } 
  10. > db.student.save({_id:1,name:"hahaBKs",age:2}) 
  11. WriteResult({ "nMatched" : 1"nUpserted" : 0"nModified" : 1 }) 
  12. > db.student.find() 
  13. "_id" : ObjectId("54fb0d853fc8173ba3302e6c"), "name" : "Viper""age" : 20 } 
  14. "_id" : ObjectId("54fb10493fc8173ba3302e6d"), "name" : "TA""age" : 18"phone" : [ "1311234567""021-87658765" ], "GPA" : { "Math" : 88"English" : 99 } } 
  15. "_id" : 1"name" : "hahaBKs""age" : 2 } 
  16. >

更改的操作用的是update方法。

用法為: db.collection.update({...},{...})

參數(shù)有兩個,***個指定要改誰,第二個指定改成什么。

但是事情沒有這么簡單,請看下面的例子。原本的打算是將名字為hahaBKs的記錄增加一個性別字段,但是發(fā)現(xiàn)除了_id的所有字段都被覆蓋掉了,只剩下了gender。這顯然不是我們的預(yù)想的結(jié)果。

  1. > db.student.find() 
  2. "_id" : ObjectId("54fb0d853fc8173ba3302e6c"), "name" : "Viper""age" : 20 } 
  3. "_id" : ObjectId("54fb10493fc8173ba3302e6d"), "name" : "TA""age" : 18"phone" : [ "1311234567""021-87658765" ], "GPA" : { "Math" : 88"English" : 99 } } 
  4. "_id" : 1"name" : "hahaBKs""age" : 2 } 
  5. > db.student.update({name:"hahaBKs"},{gender:"male"}) 
  6. WriteResult({ "nMatched" : 1"nUpserted" : 0"nModified" : 1 }) 
  7. > db.student.find() 
  8. "_id" : ObjectId("54fb0d853fc8173ba3302e6c"), "name" : "Viper""age" : 20 } 
  9. "_id" : ObjectId("54fb10493fc8173ba3302e6d"), "name" : "TA""age" : 18"phone" : [ "1311234567""021-87658765" ], "GPA" : { "Math" : 88"English" : 99 } } 
  10. "_id" : 1"gender" : "male" } 

那么問題出在哪里呢?這里我們需要用到的一個操作符$set,具體的用法以后的文章李會詳細來說。

下面我直接給出一個解決辦法的示例,如下:

  1. > db.student.insert({name:"TB",age:11,gender:"male",room:"301"}) 
  2. WriteResult({ "nInserted" : 1 }) 
  3. > db.student.find() 
  4. "_id" : ObjectId("54fb0d853fc8173ba3302e6c"), "name" : "Viper""age" : 20 } 
  5. "_id" : ObjectId("54fb10493fc8173ba3302e6d"), "name" : "TA""age" : 18"phone" : [ "1311234567""021-87658765" ], "GPA" : { "Math" : 88"English" : 99 } } 
  6. "_id" : 1"gender" : "male" } 
  7. "_id" : ObjectId("54fc521d3fc8173ba3302e6e"), "name" : "TB""age" : 11"gender" : "male""room" : "301" } 
  8. > db.student.update({name:"TB"},{$set:{age:22,classid:"1515"}}) 
  9. WriteResult({ "nMatched" : 1"nUpserted" : 0"nModified" : 1 }) 
  10. > db.student.find() 
  11. "_id" : ObjectId("54fb0d853fc8173ba3302e6c"), "name" : "Viper""age" : 20 } 
  12. "_id" : ObjectId("54fb10493fc8173ba3302e6d"), "name" : "TA""age" : 18"phone" : [ "1311234567""021-87658765" ], "GPA" : { "Math" : 88"English" : 99 } } 
  13. "_id" : 1"gender" : "male" } 
  14. "_id" : ObjectId("54fc521d3fc8173ba3302e6e"), "name" : "TB""age" : 22"gender" : "male""room" : "301""classid" : "1515" } 

上面的例子是,增加了一個name叫TB的對象,然后對其進行更改,更改的內(nèi)容包括,將原有age鍵的值11改成22,并增加一個新的鍵classid賦值“1515”。這里需要用到的操作符就是$set,用于設(shè)置鍵的值。

刪除的方法是remove。

用法是 db.collection.remove({...})

參數(shù)里寫明想需要刪除的對象的條件。

注意,當參數(shù)空著,或者空的Json對象。即db.collection.remove()和db.collection.remove({}),將把該集合中的所有文檔全部刪除!!!

  1. > db.class.insert({classname:"English",teacher:"Mr A"}) 
  2. WriteResult({ "nInserted" : 1 }) 
  3. > db.class.insert({classname:"Math",teacher:"Mr B"}) 
  4. WriteResult({ "nInserted" : 1 }) 
  5. > db.class.find() 
  6. "_id" : ObjectId("54fc54773fc8173ba3302e6f"), "classname" : "English""teacher" : "Mr A" } 
  7. "_id" : ObjectId("54fc54833fc8173ba3302e70"), "classname" : "Math""teacher" : "Mr B" } 
  8. > db.class.remove({classname:"English"}) 
  9. WriteResult({ "nRemoved" : 1 }) 
  10. > db.class.find() 
  11. "_id" : ObjectId("54fc54833fc8173ba3302e70"), "classname" : "Math""teacher" : "Mr B" } 
  12. > db.class.remove({}) 
  13. WriteResult({ "nRemoved" : 1 }) 
  14. > db.class.find() 

上面的例子中新建了一個class集合,并插入兩個文檔。其中種種,自己看吧。

用法兩種

db.collection.find({....}),其中參數(shù)是查詢對象的條件。如果find()或find({})就是全查,這和remove很類似。

db.collection.findOne({...})和find相似,但是它只會返回***個查詢到的符合條件的對象。

  1. > db.class.insert({classname:"English",teacher:"Mr AAA"}) 
  2. WriteResult({ "nInserted" : 1 }) 
  3. > db.class.insert({classname:"English",teacher:"Mr ZZZ"}) 
  4. WriteResult({ "nInserted" : 1 }) 
  5. > db.class.insert({classname:"English",teacher:"Mr WWW"}) 
  6. WriteResult({ "nInserted" : 1 }) 
  7. > db.class.insert({classname:"English",teacher:"Mr SSS"}) 
  8. WriteResult({ "nInserted" : 1 }) 
  9. > db.class.insert({classname:"French",teacher:"Mr SSS"}) 
  10. WriteResult({ "nInserted" : 1 }) 
  11. > db.class.find({}) 
  12. "_id" : ObjectId("54fc562e3fc8173ba3302e71"), "classname" : "English""teacher" : "Mr AAA" } 
  13. "_id" : ObjectId("54fc56373fc8173ba3302e72"), "classname" : "English""teacher" : "Mr ZZZ" } 
  14. "_id" : ObjectId("54fc56413fc8173ba3302e73"), "classname" : "English""teacher" : "Mr WWW" } 
  15. "_id" : ObjectId("54fc564e3fc8173ba3302e74"), "classname" : "English""teacher" : "Mr SSS" } 
  16. "_id" : ObjectId("54fc56603fc8173ba3302e75"), "classname" : "French""teacher" : "Mr SSS" } 
  17. > db.class.findOne({classname:"English"}) 
  18. "_id" : ObjectId("54fc562e3fc8173ba3302e71"), 
  19. "classname" : "English"
  20. "teacher" : "Mr AAA" 
  21. > db.class.find({classname:"English"}) 
  22. "_id" : ObjectId("54fc562e3fc8173ba3302e71"), "classname" : "English""teacher" : "Mr AAA" } 
  23. "_id" : ObjectId("54fc56373fc8173ba3302e72"), "classname" : "English""teacher" : "Mr ZZZ" } 
  24. "_id" : ObjectId("54fc56413fc8173ba3302e73"), "classname" : "English""teacher" : "Mr WWW" } 
  25. "_id" : ObjectId("54fc564e3fc8173ba3302e74"), "classname" : "English""teacher" : "Mr SSS" } 
  26. >

博文出處:http://my.oschina.net/u/1156339/blog/384073

 

責任編輯:Ophira 來源: oschina博客
相關(guān)推薦

2009-12-28 10:42:01

MPLS技術(shù)

2010-02-25 14:46:31

2009-12-21 14:37:14

2010-04-01 16:54:06

Oracle體系結(jié)構(gòu)

2011-11-30 14:12:05

JavaJVM虛擬機

2009-12-23 15:27:44

2010-09-25 12:59:33

2012-02-06 17:22:44

MySQL

2014-07-23 09:33:52

2009-07-15 13:46:26

Swing體系結(jié)構(gòu)

2009-09-11 10:38:03

LINQ體系結(jié)構(gòu)

2009-06-26 15:58:28

EJB

2023-12-26 09:33:47

2010-05-31 10:11:32

瘦客戶端

2015-09-30 10:36:03

eSpace UC客戶華為

2023-09-12 23:08:09

2020-04-15 21:43:22

JVMJavaVMware

2010-04-01 16:40:17

Oracle數(shù)據(jù)庫

2009-07-10 16:07:10

TikeSwing創(chuàng)建MVC體系結(jié)構(gòu)

2009-09-08 14:34:42

Linq to SQL
點贊
收藏

51CTO技術(shù)棧公眾號

主站蜘蛛池模板: 免费观看黄a一级视频 | 精品亚洲一区二区三区 | 亚洲国产精品视频 | 亚洲一区成人 | 欧美一区二区三区四区五区无卡码 | 亚州激情| 欧美一级黄色片在线观看 | 91视频免费在观看 | 日日碰狠狠躁久久躁婷婷 | 国产亚洲欧美在线 | 久久一热 | 久久久久国产一区二区三区 | 黄页网址在线观看 | 亚洲激情专区 | 国产精久久久久久 | 日韩精品一二三区 | 久久99深爱久久99精品 | 国产a区| 欧美在线视频免费 | 亚洲国产一区二区视频 | 欧美午夜视频 | 国内精品久久久久久久影视简单 | 中文字幕视频在线观看 | 7777奇米影视| 日韩中文字幕一区二区 | 啪一啪 | 国产午夜精品一区二区三区嫩草 | 成人在线免费视频 | 国产一区二区三区在线视频 | 性在线| 欧美1区2区 | 国产a区| 精品欧美黑人一区二区三区 | 国产精品一区二区不卡 | 全部免费毛片在线播放网站 | 三级av网址| 久久久精 | 99久久久99久久国产片鸭王 | 亚洲一区二区在线 | 91在线网 | 亚洲精品久久久久久首妖 |