一拖陆、MongoDB介紹
1抹恳、NoSQL:非關(guān)系型數(shù)據(jù)庫(kù)
在php的世界里锡搜,常見(jiàn)的非關(guān)系型數(shù)據(jù)庫(kù)有memcached橙困、redis、mongodb
2耕餐、MongoDB介紹
mongodb是針對(duì)海量數(shù)據(jù)開(kāi)發(fā)的持久化類型NoSQL凡傅,直接把數(shù)據(jù)存儲(chǔ)到硬盤。mongodb主要是存儲(chǔ)日志或者報(bào)表之類的數(shù)據(jù)肠缔。這類數(shù)據(jù)的量都是非常大的夏跷,并且缺失少許數(shù)據(jù)是無(wú)關(guān)緊要的。
mongodb語(yǔ)法與js相同明未,并且可以在mongodb里面寫(xiě)js代碼槽华,以完成特定功能。
mongodb 有庫(kù)的概念趟妥,庫(kù)的下面是集合(表)的概念猫态,集合的里面是文檔(數(shù)據(jù))的概念。
數(shù)據(jù)以文檔的方式來(lái)體現(xiàn)的,一行行的文檔都是插入的數(shù)據(jù)懂鸵。
mongodb的id默認(rèn)帶主鍵索引偏螺。主鍵索引是不能修改、不能刪除匆光,并且是必須存在套像,值是不可重復(fù)的。
3终息、MongoDB的安裝與配置
安裝
在linux中得到壓縮包解壓完成并進(jìn)入目錄夺巩,發(fā)現(xiàn)里面的內(nèi)容,可以直接使用周崭,所以直接把解壓文件夾移動(dòng)到/working
目錄下即可柳譬。
mv mongodb-linux-i686-3.2.15/ /working/mongodb
在mongodb文件夾里,mongod是服務(wù)器续镇。
多數(shù)情況下美澳,linux中的軟件在取名時(shí),文件名末尾有d的代表服務(wù)器摸航,沒(méi)有d的代表客戶端
查看幫助信息
/working/mongodb/bin/mongod --help
參數(shù):
默認(rèn)端口號(hào):27017
--logpath arg:這里的"arg"是文件制跟,不能寫(xiě)目錄
--logappend:追加寫(xiě)日志
--fork:后臺(tái)運(yùn)行
--auth:運(yùn)行的時(shí)候,要用戶驗(yàn)證
--storageEngline arg:默認(rèn)引擎:wiredTiger酱虎;但是64位支持的雨膨。32位不支持;3.0之后的32位默認(rèn)引擎要修改成mmapv1
--dbpath arg:指定一個(gè)目錄
配置參數(shù):
--port 27017
--logpath 創(chuàng)建一個(gè)目錄:logs目錄
--dbpath 創(chuàng)建一個(gè)目錄:data目錄
啟動(dòng)mongodb服務(wù)器
/working/mongodb/bin/mongod --port 27017 --fork --logpath /working/mongodb/logs/mongod.log --logappend --storageEngine mmapv1 --dbpath /working/mongodb/data/
啟動(dòng)之后檢查一下有沒(méi)有端口號(hào)和進(jìn)程號(hào)
啟動(dòng)客戶端
/working/mongodb/bin/mongo 192.168.xxx.xx:27017
4读串、快速入門
(1)數(shù)據(jù)庫(kù)(db)
查看庫(kù):show databases;
或者show dbs
進(jìn)入庫(kù):use db_name
說(shuō)明:mongodb默認(rèn)是可以進(jìn)入任意一個(gè)庫(kù)的聊记。這個(gè)庫(kù)存在不存在都可以。進(jìn)入不存在的庫(kù)恢暖,只有在庫(kù)里面有數(shù)據(jù)了排监,就會(huì)自動(dòng)創(chuàng)建這個(gè)庫(kù)。
(2)集合(collection)
查看集合:show tables;
查看集合:show collections
默認(rèn)情況下胀茵,當(dāng)你的集合下面有數(shù)據(jù)的時(shí)候社露,就會(huì)自動(dòng)創(chuàng)建這個(gè)集合 挟阻。
(3)文檔(document):插入數(shù)據(jù)
插入數(shù)據(jù): db.collection_name.insert({});
db :表示當(dāng)前庫(kù)
collection_name:集合名稱
insert:操作動(dòng)作(插入)
{} :文檔琼娘,要寫(xiě)入的數(shù)據(jù),數(shù)據(jù)格式是json附鸽。
eg:db.book.insert({name:"xiaoming", age:18, sex:2});
查看數(shù)據(jù):db.collection_name.find();
eg:db.book.find();
插入數(shù)據(jù)的時(shí)候脱拼,沒(méi)有指定id,會(huì)默認(rèn)的生成一個(gè)id的字符串坷备!
手動(dòng)插入id:id的字段名必須是_id
值必須是不重復(fù) 熄浓; db.collection_name.insert({_id:1})
eg:db.book.insert({_id:1,name:"xiaohong",age:19,sex:1});
插入多條數(shù)據(jù):db.collection_name.insert([{},{}]);
。[{},{}] 。每一個(gè)文檔赌蔑,就是一條數(shù)據(jù)俯在!
eg:db.book.insert([{_id:2,name'xiao2',age:19,sex:1},{_id:3,name:'xiao3',age:19,sex:2}]);
使用js自動(dòng)生成數(shù)據(jù):
function autoinsert(){ for(var i = 10; i < 20; i++){ db.book.insert({_id:i, name:"xiao" + i, age: i + 10, sex:1}); } } //執(zhí)行這個(gè)函數(shù) autoinsert(); //查看數(shù)據(jù) db.book.find();
(4)文檔(document):更新數(shù)據(jù)、刪除數(shù)據(jù)
更新數(shù)據(jù):db.collection_name.update({},{});
db :表示當(dāng)前庫(kù)
collection_name:集合名稱
update:操作動(dòng)作(更新)
{}:第一個(gè)文檔娃惯,更新條件
{}:第二個(gè)文檔跷乐,更新的值
eg:db.book.update({name:"xiaohong"}, {age:10});
注:此用法,在更新之后趾浅,只保留更新的值與ID愕提,其它的字段都不在了,因此使用下面的方法
選擇器:
$set:只修改更新的內(nèi)容皿哨,其它值保持不變
$inc:數(shù)值型值浅侨,指定自增多少,或者自減多少
db.collection_name.update({},{});
{}:第一個(gè)文檔证膨,更新條件
{}:第二個(gè)文檔如输,更新的值。第二個(gè)文檔的內(nèi)容寫(xiě)法:$set:{更新的內(nèi)容}
eg:
db.book.update({name:"xiaoming"},{$set:{age:10}});
指定自增:$inc
db.book.update({_id:2}, {$inc:{age:1}});
指定直減:$inc
db.book.update({_id:11}, {$inc:{age:-1}});
修改內(nèi)容的數(shù)量:$set
db.book.update({age:20}, {$set:{sex:2}});
mongodb是一個(gè)海量的數(shù)據(jù)庫(kù)央勒,默認(rèn)只是更新匹配到的第一個(gè)值挨决!
更新數(shù)據(jù)的量,第三個(gè)文檔:db.collection_name.update({},{},{});
{}:第三個(gè)文檔里面可以有二個(gè)值
? multi:true 订歪。true值脖祈,表示滿足匹配條件的數(shù)據(jù),全部更新刷晋;false(默認(rèn))值盖高,表示更新第一條匹配到的數(shù)據(jù)。
? upsert:true 眼虱。true值喻奥,表示沒(méi)有匹配到任何數(shù)據(jù),轉(zhuǎn)成插入該數(shù)據(jù)捏悬;false(默認(rèn))值撞蚕,表示沒(méi)有匹配到任何數(shù)據(jù),放棄操作。與MySQL里面的replace語(yǔ)法效果相同斧账。
更新全部匹配的值:multi:true
eg:db.book.update({age:20},{$set:{sex:3}},{multi:true});
更新數(shù)據(jù)的時(shí)候掘宪,沒(méi)有匹配的值,插入該數(shù)據(jù):upsert:true
eg:db.book.update({age:18},{$set:{sex:2}},{upsert:true});
upsert與multi是可以同時(shí)使用的刀疙!
db.book.update({age:20}, {$set:{sex:2}},{upsert:true,multi:true});
刪除數(shù)據(jù):db.conllection_name.remove({});
db :表示當(dāng)前庫(kù)
collection_name:集合名稱
remove:操作動(dòng)作(刪除)
{}:第一個(gè)文檔,刪除條件扫倡;空文檔谦秧,匹配全部數(shù)據(jù)
eg:db.book.remove({age:18});
刪除數(shù)據(jù)的時(shí)候,默認(rèn)是匹配到多少,刪除多少疚鲤。
刪除數(shù)據(jù)的量锥累,第二個(gè)文檔:db.conllection_name.remove({},{});
{}:第二個(gè)文檔里面可以有一個(gè)值
? justOne:true 。true值集歇,表示滿足匹配條件的數(shù)據(jù)揩悄,刪除一條;false(默認(rèn))值鬼悠,表示匹配到的數(shù)據(jù)删性,全部刪除。
eg:db.book.remove({age:20},{justOne:true});
刪除空文檔的效果:db.book.remove({});
焕窝,此時(shí)的數(shù)據(jù)就全部刪除了
(5)刪除collection與刪除db
刪除集合:db.collection_name.drop();
eg:db.book.drop();
刪除數(shù)據(jù)庫(kù):db.dropDatabase();
重點(diǎn)強(qiáng)調(diào):要?jiǎng)h除哪一庫(kù)蹬挺,必須在這個(gè)庫(kù)里面操作!
(6)瞬間完成
上面的插入它掂,刪除和更新操作都是瞬間完成的巴帮,它們不需要等待數(shù)據(jù)庫(kù)響應(yīng)。這樣的實(shí)現(xiàn)可以獲取高性能虐秋,速度非抽偶耄快,只會(huì)受客戶端發(fā)送速度和網(wǎng)絡(luò)速度的制約客给。但由于不會(huì)獲取服務(wù)器狀態(tài)用押,所以不能保證操作順利完成。這對(duì)于付費(fèi)系統(tǒng)靶剑,安全性較高的系統(tǒng)是不可行的蜻拨,此時(shí)對(duì)這些操作需要使用它們的安全版本。安全版本會(huì)在操作執(zhí)行后立即運(yùn)行g(shù)etLastError命令桩引,來(lái)檢查是否執(zhí)行成功缎讼。如果失敗一般會(huì)拋出可捕獲的異常,然后我們可以在代碼中處理坑匠。
5血崭、MongoDB進(jìn)階
(1)MongoDB幫助系統(tǒng)
系統(tǒng)幫助:help
help后面不要加分號(hào)[;]
庫(kù)幫助:db.help();
集合幫助:db.collection_name.help();
操作動(dòng)作幫助:db.collection_name.find().help();
mongodb的幫助信息,非常的方便厘灼,可以直接實(shí)現(xiàn)夹纫。
(2)查詢
$eq(等于);$ne(不等于)手幢; $lt(小于)捷凄;$lte(小于等于);$gt(大于)围来;$gte(大于等于);$in(包含);$nin(不包含)监透;$and(并且)桶错;$or(或者)
- 等于:
db.collection_name.find({name:{$eq:'xiao0'}});
- eg:
db.book.find({name:{$eq:"xiao0"}});
- eg:
- 不等于:
db.collection_name.find({name:{$ne:'xiao0'}});
- eg:
db.book.find({name:{$ne:"xiao0"}});
- eg:
- 小于:
db.collection_name.find({age:{$lt:14}});
- eg:
db.book.find({age:{$lt:14}});
- eg:
- 小于等于:
db.collection_name.find({age:{$lte:14}});
- eg:
db.book.find({age:{$lte:14}});
- eg:
- 大于:
db.collection_name.find({age:{$gt:14}});
- eg:
db.book.find({age:{$gt:14}}); ";
- eg:
- 大于等于:
db.collection_name.find({age:{$gte:14}}) ;
- eg:
db.book.find({age:{$gte:14}});
- eg:
總結(jié):$eq $ne $lt $lte $gt $gte
db.collection_name.find({field:{$eq:value}})
- 包含:$in;
db.collection_name.find({field:{$in:[value,value]}});
- eg:
db.book.find({age:{$in:[13,14,15]}});
- 不包含:$nin胀蛮;
db.collection_name.find({field:{$nin:[value,value,value]}});
- eg:
db.book.find({age:{$nin:[13,14,15]}});
總結(jié):$in $nin
db.collection_name.find({field:{$in:[v,v,v]}});
- 并且:$and
db.collection_name.find({$and:[{age:1},{name:”xiao1”}]});
- eg1:
db.book.find({$and:[{name:"xiao0"},{age:10}]});
- eg2:
db.book.find({$and:[{name:"xiao0"}, {age:{$lt:11}}]});
- 或者:$or
db.collection_name.find({$or:[{field:value},{field:value}]});
- eg:
db.book.find({$or:[{name:"xiao0"},{age:{$gt:18}}]});
總結(jié):$and $or
db.collection_name.find({$and:[{field:value},{field:value}]});
查詢條件說(shuō)明:
操作動(dòng)作find示例院刁,演示了匹配條件。其它的操作動(dòng)作只要有匹配條件的粪狼,都可以使用這些匹配條件退腥。
例如,操作動(dòng)作update(更新)的第一個(gè)文檔再榄,就是匹配條件,這些就可以完全被使用嗅蔬。
例如疾就,操作動(dòng)作remove(刪除)的第一個(gè)文檔,就是匹配條件鸟废,這些就可以完全被使用姑荷。
查詢動(dòng)作(find)的過(guò)濾動(dòng)作介紹:
- 內(nèi)容跳過(guò):skip
db.book.find().skip(2);
skip(n) :number是一個(gè)整型。
- 內(nèi)容顯示:limit
db.book.find().limit(2);
limit(n):number是一個(gè)整型 兰英。
- 內(nèi)容統(tǒng)計(jì):count
db.book.find().count();
- 內(nèi)容統(tǒng)計(jì):size
db.book.find().size();
- 內(nèi)容排序:sort
field:value
value === 1 :升序畦贸;
db.book.find().sort({name:1});
value === -1 :降序楞捂;
db.book.find().sort({name:-1});
- 實(shí)現(xiàn)分頁(yè)效果:skip與limit
db.book.find().skip(2).limit(2);
count默認(rèn)是不認(rèn)可skip與limit的操作的。
- 使用skip或者limit的時(shí)候:
db.book.find().skip(8).limit(2).count(true);
- 約束返回?cái)?shù)據(jù):
db.collection_name.find({},{});
{}:第二個(gè)文檔寨闹,表明返回哪些字段的數(shù)據(jù)胶坠。
_id:value 。0值繁堡,不返回沈善;1值乡数,返回
設(shè)置注意:
同時(shí)設(shè)置_id與其它字段時(shí)。_id是要返回闻牡,其它字段必須是返回净赴;_id是不返回,其它字段可以返回或者不返回罩润。
設(shè)置多個(gè)其它字段時(shí)玖翅,其它字段的設(shè)置狀態(tài)必須保持一致。
db.book.find({},{_id:1});
_id如果返回割以,其它字段也必須返回金度;
_id如果不返回,其它字段可以返回或者不返回:
db.book.find({},{_id:0, name:1,age:1});
严沥,此時(shí)就是返回的字段是:name猜极,age
設(shè)置多個(gè)其它字段時(shí),其它字段的設(shè)置狀態(tài)必須保持一致:
db.book.find({},{_id:0, name:0,age:0});
下面是錯(cuò)誤寫(xiě)法:
db.book.find({},{_id:0, name:0,age:1});
- 整型與字符:
db.book.insert({_id:10,name:"xiao10",age:"19",sex:1});
- 查看age是19的:
db.book.find({age:19});
說(shuō)明:mongodb里面祝峻,是區(qū)分字符數(shù)字與整型的魔吐。
- 集合下的統(tǒng)計(jì):count
db.book.count({_id:{$gt:15}});
在Mongodb里面有很多方法實(shí)現(xiàn)相同的效果,掌握一種就可以了 莱找。
(3)聚合
db.collection_name.aggregate({});
{}:文檔里面可以有三個(gè)值
$match:{}
? {} 這個(gè)文檔里面的值酬姆,同find的查找內(nèi)容別無(wú)二致辞色。
$group:{}
? {} 這個(gè)文檔里面的值,非常重要立美。
? _id :這個(gè)是必須寫(xiě)的建蹄,強(qiáng)制要求的,文檔有強(qiáng)調(diào)劲腿。
例:
{_id:'123'};
給每一行文檔一個(gè)固定的值是123挥吵,對(duì)文檔的123值進(jìn)行分組蔫劣。分組結(jié)果:_id是字段个从,值是123嗦锐。
{_id:"$sex"};
對(duì)每一行文檔里面的sex字段值進(jìn)行分組。分組結(jié)果:_id是字段碳默,值是sex字段不重復(fù)的值。
{_id:"$sex", fieldname:{$sum:1}};
給每一行文檔一個(gè)固定的值是1该抒。對(duì)每一行文檔里面的sex字段值進(jìn)行分組,統(tǒng)計(jì)每一個(gè)分組里面固定值1的和(sum)欧引,并且把和的結(jié)果給字段fieldname芝此。分組結(jié)果:_id是字段癌蓖,值是sex不重復(fù)的值;fieldname是字段用僧,值是統(tǒng)計(jì)固定值1的結(jié)果责循。
{_id:"$sex", fieldname {$sum: "$age"}}
對(duì)每一行文檔里面的age字段值進(jìn)行分組秸抚,統(tǒng)計(jì)每一個(gè)分組里面sex值的和(sum)剥汤,并且把和的結(jié)果給字段fieldname。分組結(jié)果:_id是字段鹿驼,值是age不重復(fù)的值;fieldname是字段舷蟀,值是統(tǒng)計(jì)sex值的結(jié)果野宜。
$sum :求和;$avg :求平均值虎敦;$max :求最大值其徙;$min:求最小值。
$sort:{}
{}這個(gè)文檔里面的值闹获,同find的排序動(dòng)作(sort)別無(wú)二致龟虎。 age:1 鲤妥。值1旭斥,升序;值-1羡滑,降序
-
$match;
db.quan6.aggregate({$match:{_id:{$lt:5}}});
eg:
db.book.aggregate({$match:{_id:{$lt:5}}});
-
$group
- eg1:
db.book.aggregate({$group:{_id:123}});
- eg2:
db.book.aggregate({$group:{_id:"$sex",persions:{$sum:1}}});
- eg3:
db.book.aggregate({$group:{_id:"$sex",persions:{$sum:"$age"}}});
- eg1:
統(tǒng)計(jì)所有人年齡的平均值:
db.school.aggregate({$group:{_id:1,avg:{$avg:"$age"}}});
統(tǒng)計(jì)不同性別的年齡的平均值:
db.school.aggregate({$group:{_id:"$sex",avg:{$avg:"$age"}}});
統(tǒng)計(jì)所有人的年齡的最大值:
ab.school.aggregate({$group:{_id:1,man:{$min:"$age"}}});
- $sort
- 升序:
db.school.aggregate({$sort:{sex:1}});
- 降序:
db.school.aggregate({$sort:{sex:-1}});
- 升序:
三大值都單詞操作完成了:組合使用职祷!
db.collection_name.aggregate([{},{},{}]);
三個(gè)大的類型,可以寫(xiě)一個(gè)泥耀,寫(xiě)二個(gè)痰催,或者寫(xiě)三個(gè)。
$match與$group
db.school.aggregate({$match:{_id:{$lt:8}}},{$group:{_id:"$sex",avg:{$avg:"$_id"}}});
$match與$sort
db.school.aggregate({$match:{_id:{$lt:8}}},{$sort:{age:-1}});
$group與$sort
db.school.aggregate({$group:{_id:"$sex", agemax:{$max:"$age"}}},{$sort:{agemax:1}});
發(fā)現(xiàn):2個(gè)一起使用時(shí)缝裁,第一個(gè)結(jié)果就是第二個(gè)的參數(shù)
三個(gè)連用:
db.school.aggregate([{$match:{_id:{$ne:10}}},{$group:{_id:"$sex",agesum:{$sum:"$age"}}},{$sort:{_id:1}}]);
最好的使用順序就是match然后是group再是sort
(4)mapReduce:批量操作
db.collection_name.mapReduce(map, reduce, {});
map:函數(shù)名稱。
掃描集合中的所有文檔扰才,把每一行文檔的數(shù)據(jù)拿來(lái)處理。每一行文檔數(shù)據(jù)琅捏,都執(zhí)行一次map函數(shù)。
執(zhí)行map函數(shù)搜吧,this表示正在執(zhí)行的這行文檔對(duì)象。使用某一個(gè)字段蜒程,就使用this.field昭躺。
例如:獲取年齡(this.age)
函數(shù)執(zhí)行完成礼殊,想要存儲(chǔ)結(jié)果晶伦,必須調(diào)用內(nèi)置emit函數(shù)族沃。
該函數(shù)必須有二個(gè)參數(shù):emit(v1, v2)。
function map(){ emit(this.sex, this.age) }
假如:文檔數(shù)量有4個(gè)漓糙!map實(shí)現(xiàn)是emit(this.sex, this.age)
掃描第一行文檔的時(shí)候,產(chǎn)生的結(jié)果:array(sex => array(age))
掃描第二行文檔的時(shí)候,產(chǎn)生的結(jié)果:array(sex => array(age, age))
掃描第三行文檔的時(shí)候盗棵,產(chǎn)生的結(jié)果:array(sex => array(age, age, age))
掃描第四行文檔的時(shí)候鲫竞,sex和上面的三個(gè)不一樣了是牢,產(chǎn)生的結(jié)果:
? array(sex => array(age, age, age), sex => array(age))
數(shù)值:(age : 10; sex :1); (age:11; sex:1); age: 12; sex:1); (age:13; sex:0)
emit(this.sex, this.age)
掃描第一行文檔的時(shí)候批什,產(chǎn)生的結(jié)果:array(1 => array(10))
掃描第二行文檔的時(shí)候驻债,產(chǎn)生的結(jié)果:array(1 => array(10, 11))
掃描第三行文檔的時(shí)候,產(chǎn)生的結(jié)果:array(1 => array(10, 11, 12))
掃描第四行文檔的時(shí)候形葬,產(chǎn)生的結(jié)果:array(1 => array(10, 11, 12), 0 => array(13))
reduce:函數(shù)名稱合呐。該函數(shù)有二個(gè)參數(shù)(v1, v2)
? 第一個(gè)參數(shù),是emit函數(shù)的key值
? 第二個(gè)參數(shù)笙以,是emit函數(shù)的value值(數(shù)組)
reduce函數(shù)調(diào)用的次數(shù)淌实,由emit函數(shù)存儲(chǔ)的key數(shù)量決定。emit函數(shù)有二個(gè)key,reduce函數(shù)就調(diào)用二次。
reduce函數(shù)轻姿,就是去循環(huán)emit函數(shù)的結(jié)果
{}:文檔炊昆。設(shè)置不同作用的值一個(gè)
? out:{inline:1} 留美。打印到屏幕
? out:{replace:”collection_name”} 。結(jié)果存儲(chǔ)到collection_name集合里面
collection_name集合存在就覆蓋,不存在就創(chuàng)建凄吏!
實(shí)現(xiàn)map函數(shù):
獲得sex與age,存儲(chǔ)起來(lái)
function map(){
var age = this.age;
var sex = this.sex;
emit(sex,age);
}
實(shí)現(xiàn)reduce函數(shù):
求的不同性別年齡的和拱她!
function reduce(sex, ages){
var agesum = Array.sum(ages);
var res = sex + '-' + agesum;
return res;
}
實(shí)踐:
db.quan6.mapReduce(map,reduce,{out:{inline:1}});
(5)索引
- 查看索引:
db.collection_name.getIndexes();
- eg:
db.book.getIndexes();
- eg:
- 創(chuàng)建索引:
db.collection_name.createIndex({field:1});
field:1 。1值是升序索引妄均;-1值是降序索引。
? eg:db.book.createIndex({age:1});
之所以寫(xiě)索引名稱,就是方便管理
- 刪除索引:
db.collection_name.dropIndex(索引名);
- eg:
db.book.dropIndex('age_1');
- eg:
- 刪除主鍵索引:
db.book.dropIndex('_id_');
- 創(chuàng)建唯一索引:
db.collection_name.createIndex({field:1},{unique:true});
unique:true :是true的時(shí)候逊笆,才是唯一索引症虑,強(qiáng)調(diào)在創(chuàng)建的時(shí)候沈条,值必須是沒(méi)有重復(fù)的
? eg:db.book.createIndex({name:1},{unique:true});
- 測(cè)試唯一索引:
db.collection_name.insert({});
- eg:
db.book.insert({_id:10,name:"xiao9",age:19,sex:1});
- eg:
- 不使用重復(fù)的值:
db.book.insert({_id:10,name:"xiao10",age:19,sex:1});
- 查看索引被使用了:
db.collection_name.find({''}).explain('executionStats');
- eg:
db.book.find({name:"xiao9"}).explain('executionStats');
- eg:
- 創(chuàng)建一個(gè)降序索引:
db.collection_name.createIndex({field:-1});
- eg:
db.book.createIndex({age:-1});
- eg:
- 刪除全部索引憨攒,不包含主鍵索引:
db.collection_name.dropIndexes();
- eg:
db.book.reopIndexes();
- eg:
索引是為了海量數(shù)據(jù)準(zhǔn)備的,所有有很多不一樣的特性雏掠。都是因?yàn)閿?shù)據(jù)不一樣而產(chǎn)生的。mongodb還有很多種索引的類型庇楞。
(6)固定集合
就是提前創(chuàng)建好集合,并且設(shè)定它有大小溃论。里面的數(shù)據(jù)荐吵,不能刪除消略。數(shù)據(jù)存儲(chǔ)滿了之后豪硅,使用最近最少原則刪除內(nèi)容柱彻。
作用琳猫,當(dāng)項(xiàng)目有一些數(shù)據(jù)伟叛,是前面的數(shù)據(jù)無(wú)用的。保持一定的數(shù)據(jù)量脐嫂,就可以使用它统刮。
db.createCollection('collection_name', {});
文檔的說(shuō)明:
? capped:true 。true值的時(shí)候账千,表示是創(chuàng)建的固定集合侥蒙。必須的值
? size:50 。設(shè)置集合的存儲(chǔ)空間大小匀奏。必須的值
max:3 鞭衩。設(shè)置集合最大的文檔數(shù)量⊥奚疲可選的值
強(qiáng)調(diào):max與size這二個(gè)限制大小的操作论衍,任何一個(gè)先到達(dá),就開(kāi)始執(zhí)行最近最少使用原則刪除數(shù)據(jù)聚磺。
- 創(chuàng)建一個(gè):
db.createCollection('python',{capped:true,size:50,max:3});
- 查看集合:
show tables;
- 插入數(shù)據(jù):
db.python.insert({_id:1,name:"xiao1",age:12});
- 查看數(shù)據(jù):
db.python.find();
- 更新數(shù)據(jù):
db.python.update({_id:2},{$set:{age:22}});
- 刪除數(shù)據(jù):
db.python.remove({_id:5});
- 刪除集合:
db/python.drop();
固定集合坯台,是可以刪除的。但是里面的數(shù)據(jù)是不能刪除的瘫寝。只能插入與更新蜒蕾。
(7)GridFS功能
就是把文件以二進(jìn)制的形式,上傳到mongodb里面存儲(chǔ)的焕阿。獲取出來(lái)的時(shí)候咪啡,直接轉(zhuǎn)換成了曾經(jīng)的模式。
①找到工具:在目錄/working/mongodb/bin
下的mongofiles
文件暮屡。
它可以把任何文件上傳到mongodb里面瑟匆。無(wú)論是圖片,還是壓縮文件,還是文本文件愁溜。都可以以二進(jìn)制的形式,存儲(chǔ)到mongodb的數(shù)據(jù)庫(kù)里面外厂。
mongodb會(huì)以2G的空間大小冕象,劃分出區(qū)域來(lái)存儲(chǔ)這些內(nèi)容。這個(gè)時(shí)候汁蝶,2G來(lái)劃分渐扮,就很難產(chǎn)生硬盤的碎片!對(duì)搜索數(shù)據(jù)就會(huì)有性能的提升掖棉。
②查看幫助信息并確定參數(shù):/wordking/mongodb/bin/mongofiles --help
確定參數(shù):
list:顯示墓律;search:查詢;put:上傳幔亥;get:下載耻讽;delete:刪除
上傳與下載的時(shí)候,指定文件路徑帕棉。
③上傳文件:/working/mongodb/bin/mongofiles --db=data put install --local=/root/install.log.syslog
顯示一下:/working/mongodb/bin/mongofiles list --db=data
④下載文件:/working/mongodb/bin/mongofiles get install --local=/home/install.log --db=data
⑤搜索:/working/mongodb/bin/mongofiles search a --db=data
自帶模糊匹配
刪除:/working/mongodb/bin/mongofiles delete apr --db=data
6针肥、MongoDB的用戶管理
(1)MongoDB中的權(quán)限角色
角色:
收銀員(虛擬):收錢,發(fā)錢香伴。
? 權(quán)限是掛在角色上面慰枕。
李白:擁有收銀員的角色
? 權(quán)限:收錢,發(fā)錢即纲。
? 用戶是要有角色的具帮,通過(guò)角色就有相應(yīng)的權(quán)限。
mongodb里面是使用的這種權(quán)限低斋。還是有其它權(quán)限管理的蜂厅。
mongodb里面默認(rèn)的角色:
庫(kù)的角色:
read :讀的權(quán)限
readWrite :讀寫(xiě)的權(quán)限
userAdmin :管理庫(kù)的權(quán)限
集群的角色:
readAnyDatabase :集群的讀的權(quán)限
readWriteAnyDatabase :集群的讀寫(xiě)的權(quán)限
userAdminAnyDatabase :集群的管理庫(kù)的權(quán)限
管理員:root
mongodb里面有很多已經(jīng)設(shè)定好的角色,太多了拔稳,需要的在看
(2)開(kāi)啟MongoDB中的權(quán)限控制
啟動(dòng)mongodb服務(wù)器的時(shí)候葛峻,加上參--auth就可以了。開(kāi)啟之后巴比,登錄mongodb服務(wù)器术奖,就必須要使用賬戶與密碼。
注意:在開(kāi)啟賬戶與密碼的時(shí)候轻绞,一定一定要提前設(shè)置好有管理員的權(quán)限(至少)采记。
提前設(shè)置好:集群的管理庫(kù)的權(quán)限
db.createUser({
user:'username',
pwd:'password',
roles:[{role:'rolename', db:'管理的庫(kù)'}]
})
重點(diǎn)介紹:mongodb里面用戶是屬于某一個(gè)庫(kù)的。必須在這個(gè)庫(kù)里面才能使用這個(gè)用戶政勃。
創(chuàng)建管理員:
注意唧龄,必須先進(jìn)入admin這個(gè)庫(kù)。這個(gè)庫(kù)曾經(jīng)是管理員的庫(kù)奸远,然后現(xiàn)在默認(rèn)是自己創(chuàng)建用戶的時(shí)候既棺,才生成讽挟。以前是自帶的。所有現(xiàn)在創(chuàng)建第一個(gè)管理員丸冕,保持和曾經(jīng)一樣耽梅,先進(jìn)入這個(gè)庫(kù)。在這里創(chuàng)建一個(gè)管理員胖烛。
1)進(jìn)入admin庫(kù)
use admin
2)創(chuàng)建一個(gè)管理員
db.createUser({
user:"zhang",
pwd:"123456",
roles:[{role:"userAdnubAnyDatabase", db:"admin"}] //權(quán)限是集群的管理庫(kù)的眼姐,屬于admin庫(kù)
})
3)查看當(dāng)前庫(kù)
show collections
查看數(shù)據(jù):db.system.indexes.find();
,這個(gè)就是索引佩番。
查看創(chuàng)建用戶名信息:db.system.users.find();
4)客戶端退出
exit
5)停止服務(wù)器
先查看進(jìn)程众旗,通過(guò)進(jìn)程來(lái)關(guān)閉!ps aux | grep mongod
使用kill 的時(shí)候趟畏,注意贡歧,一定不要使用-9來(lái)關(guān)閉。因?yàn)閙ongodb里面的官方文檔說(shuō)的拱镐,不要使用艘款。
如果你使用了-9,有可能就啟動(dòng)不起來(lái)了沃琅。如果你啟動(dòng)不起來(lái)了哗咆。就查看一下目錄:
/working/mongodb/data
,刪除data目錄下面的mongod.lock即可益眉。
6)啟動(dòng)服務(wù)器晌柬,加上—auth參數(shù)
/working/mongodb/bin/mongod --port 27017 --fork --logpath /working/mongodb/logs/mongod.log --logappend --storageEngine mmapv1 --dbpath /working/mongodb/data/ --auth
7)使用客戶端登錄:
/working/mongodb/bin.mongo 192.168.xxx.xx:27017
此時(shí)登錄成功后如果要show dbs
時(shí),如果發(fā)現(xiàn)報(bào)錯(cuò)了郭脂,這是因?yàn)闆](méi)有權(quán)限年碘。
用戶是屬于庫(kù)的,所以我們要進(jìn)入用戶所在的庫(kù)展鸡,進(jìn)行登錄屿衅。
選擇use admin
庫(kù)后,再進(jìn)行登錄:db.auth('zhang','123456');
莹弊,顯示1涤久,則是登錄成功。再查看當(dāng)前庫(kù):show collections;
忍弛,此時(shí)也會(huì)報(bào)錯(cuò)响迂,'zhang'是管理員,沒(méi)有查看的權(quán)限细疚。
8)使用管理員蔗彤,創(chuàng)建一個(gè)用戶。
db.createUser({
user:"adminr",
pwd:"123456",
roles:[{role:"read",db:"admin"}] //權(quán)限為讀,用戶屬于admin這個(gè)庫(kù)
})
使用這個(gè)新的用戶:use admin
選擇庫(kù)后然遏,進(jìn)行登錄:db.auth("adminr","123456");
贫途,查看庫(kù):show tables;
,是可以查看的啦鸣,但是繼續(xù)查看db.system.users.find();
時(shí)又會(huì)報(bào)錯(cuò)潮饱,還是沒(méi)有權(quán)限。
9)進(jìn)入到管理員
use admin
诫给,并且登錄db.auth('zhang','123456');
10)給quan庫(kù)里面撞見(jiàn)一個(gè)readWrite的用戶
use quan
db.createUser({
user:"quanrw",
pwd:'123456',
roles:[{roles:"readWrite", db:"quan"}]
})
使用這個(gè)賬戶:use quan
,登錄一下:db.auth('quanrw', '123456');
啦扬,查看庫(kù):show tables;
中狂,這個(gè)庫(kù)里沒(méi)有東西,但是可以往里面寫(xiě)內(nèi)容:db.quan.insert({_id:1, name:"123"});
扑毡,使用一下讀操作:db.quan.find();
即可讀出數(shù)據(jù)胃榕。
7、使用PHP操作MongoDB
(1)安裝php_mongo擴(kuò)展
給php安裝mongodb的擴(kuò)展瞄摊,讓php成為可以連接mongodb服務(wù)器的客戶端勋又!
http://pecl.php.net/package-search.php?pkg_name=mongo&bool=AND&submit=Search
mongo有2個(gè)擴(kuò)展,任意選擇一個(gè)都可以换帜。但是mongo擴(kuò)展只能是php7以下的楔壤,mongodb擴(kuò)展支持7以上的。
安裝linux擴(kuò)展:
得到擴(kuò)展的壓縮包惯驼,放到linux下蹲嚣,解壓:tar -zxf /存放路徑/mongodb-1.3.4.tgz
進(jìn)入到該目錄下,再確定好PHP版本后安裝mongodb擴(kuò)展祟牲, 我們要給這個(gè)安隙畜。就要使用里面的phpize與php-config這2個(gè)程序。只能是這個(gè)版本的说贝,不能混用 议惰。
編譯安裝:./configure --with-php-config=/working/php7/bin/php-config && make && make install
安裝完成后查看擴(kuò)展,在目錄:/working/php7/lib/php/extensions/no-debug-zts-20160303/
下乡恕,會(huì)有一個(gè)mongodb.so
文件言询。
配置php.ini信息:vim /working/php7/etc/php.ini
打開(kāi)的這個(gè)php.ini配置文件,肯定是和phpize與php-config同一個(gè)版本下面的几颜。
進(jìn)入文件后倍试,在大概929行左右,添加:extension=mongodb.so
驗(yàn)證一下:/working/php7/bin/php -m
蛋哭,如果出現(xiàn)mongodb時(shí)說(shuō)明安裝成功县习。
(2)使用PHP連接MongoDB
mongodb擴(kuò)展與mongo擴(kuò)展,他們的操作方式是完全不一樣的。
你使用哪一個(gè)擴(kuò)展躁愿,就使用哪一個(gè)擴(kuò)展的說(shuō)明文檔叛本,進(jìn)行操作。
$manager = new MongoDB\Driver\Manager("mongodb://quanrw:123456@192.168.xxx.xx:27017/quan");
var_dump($manager);
如果配置信息沒(méi)有錯(cuò)誤彤钟,可以打印出相關(guān)的對(duì)象信息来候。
(3)使用PHP+MongoDB實(shí)現(xiàn)CURD操作
$insert = new MongoDB\Driver\BulkWrite;
$insert -> insert(['_id' => 1, 'name' => 'xiao1', 'age' => 10, 'sex' => 1]);
$insert -> insert(['_id' => 2, 'name' => 'xiao2', 'age' => 10, 'sex' => 1]);
$insert -> insert(['_id' => 3, 'name' => 'xiao3', 'age' => 10, 'sex' => 2]);
$insert -> insert(['_id' => 4, 'name' => 'xiao4', 'age' => 10, 'sex' => 2]);
$manager = new MongoDB\Driver\Manager("mongodb://quanrw:123456@192.168.xxx.xx:27017/quan");
$manager -> executeBulkWrite('quan.quan6', $insert);
var_dump($manager);
訪問(wèn)頁(yè)面后可以看到打印出的數(shù)據(jù)信息,可以再進(jìn)入數(shù)據(jù)庫(kù)驗(yàn)證數(shù)據(jù):
show tables;
db.quan6.find();
更新數(shù)據(jù):
$update = new MongoDB\Driver\BulkWrite;
//mongodb寫(xiě)的時(shí)候逸雹,一定要寫(xiě)單引號(hào)
$update -> update(['sex' => ['$eq' => 1]], ['$set' => ['age' => 11]], ['multi' => true, 'upsert' => true]);
//連接mongodb數(shù)據(jù)庫(kù)
$manager = new MongoDB\Driver\Manager("mongodb://quanrw:123456@192.168.xxx.xx:27017/quan");
//執(zhí)行構(gòu)建
$manager -> executeBulkWrite('quan.quan6', $update);
var_dump($manager);
刪除數(shù)據(jù):
$delete = new MongoDB\Driver\BulkWrite;
//在php里面limit是真的時(shí)候营搅,表示刪除一條數(shù)據(jù)
$delete -> delete(['age' => 10], ['limit' => 1]);
//連接mongodb數(shù)據(jù)庫(kù)
$manager = new MongoDB\Driver\Manager("mongodb://quanrw:123456@192.168.xxx.xx:27017/quan");
//執(zhí)行構(gòu)建
$res = $manager -> executeBulkWrite('quan.quan6', $delete);
var_dump($res);
查詢數(shù)據(jù):
//查詢條件
$filter = ['_id' => ['$in' => [1, 2, 4]]];
//過(guò)濾選擇
$options = [
//查詢想要的字段:字段值如果對(duì)應(yīng)的是0,不顯示梆砸。對(duì)應(yīng)的值是1转质,就是顯示
'projection' => ['_id' => 0, 'name' => 1, 'age' => 1],
'sort' => ['age' => 1],
'skip' => 1,
'limit' => 1,
];
$query = new MongoDB\Driver\Query($filter, $options);
//連接MongoDB服務(wù)器
$manager = new MongoDB\Driver\Manager("mongodb://quanrw:123456@192.168.xxx.xx:27017/quan");
$cursor = $manager -> executeBulkWrite('quan.quan6', $query);
foreach($cursor as $value)
{
var_dump($value);
echo '<br>';
}
聚合:
//聚合使用
$options = [
//aggregate表示聚合,對(duì)應(yīng)的是聚合名稱
'aggregate' => 'quan6',
'pipeline' => [
['$match' => ['_id' => ['$in' => [1, 2, 4]]]],
['$group' => ['_id' => '$sex', 'agesum' => ['$sum' => '$age']]],
['$sort' => ['agesum' => 1]],
],
'cursor' => new stdClass,
];
//構(gòu)架聚合
$command = new MongoDB\Driver\Command($options);
//連接MongoDB服務(wù)器
$manager = new MongoDB\Driver\Manager("mongodb://quanrw:123456@192.168.xxx.xx:27017/quan");
//執(zhí)行構(gòu)建
$cursor = $manager -> executeBulkWrite('quan', $command);
foreach($cursor as $val)
{
var_dump($val);
echo '<br>';
}