游标
for(i=0; i<100; i++) {
db.c.insert({x : i});
}
var cursor = db.c.find();
while (cursor.hasNext()) {
obj = cursor.next();
print(obj.x);
}
#limit和skip
> db.c.find().limit(3)
{ "_id" : ObjectId("52b95bc791af8553649391c8"), "x" : 0 }
{ "_id" : ObjectId("52b95bc791af8553649391c9"), "x" : 1 }
{ "_id" : ObjectId("52b95bc791af8553649391ca"), "x" : 2 }
> db.c.find().skip(3)
{ "_id" : ObjectId("52b95bc791af8553649391cb"), "x" : 3 }
{ "_id" : ObjectId("52b95bc791af8553649391cc"), "x" : 4 }
{ "_id" : ObjectId("52b95bc791af8553649391cd"), "x" : 5 }
{ "_id" : ObjectId("52b95bc791af8553649391ce"), "x" : 6 }
{ "_id" : ObjectId("52b95bc791af8553649391cf"), "x" : 7 }
{ "_id" : ObjectId("52b95bc791af8553649391d0"), "x" : 8 }
{ "_id" : ObjectId("52b95bc791af8553649391d1"), "x" : 9 }
{ "_id" : ObjectId("52b95bc791af8553649391d2"), "x" : 10 }
{ "_id" : ObjectId("52b95bc791af8553649391d3"), "x" : 11 }
{ "_id" : ObjectId("52b95bc791af8553649391d4"), "x" : 12 }
{ "_id" : ObjectId("52b95bc791af8553649391d5"), "x" : 13 }
{ "_id" : ObjectId("52b95bc791af8553649391d6"), "x" : 14 }
{ "_id" : ObjectId("52b95bc791af8553649391d7"), "x" : 15 }
{ "_id" : ObjectId("52b95bc791af8553649391d8"), "x" : 16 }
{ "_id" : ObjectId("52b95bc791af8553649391d9"), "x" : 17 }
{ "_id" : ObjectId("52b95bc791af8553649391da"), "x" : 18 }
{ "_id" : ObjectId("52b95bc791af8553649391db"), "x" : 19 }
{ "_id" : ObjectId("52b95bc791af8553649391dc"), "x" : 20 }
{ "_id" : ObjectId("52b95bc791af8553649391dd"), "x" : 21 }
{ "_id" : ObjectId("52b95bc791af8553649391de"), "x" : 22 }
has more
> db.c.find().skip(10).limit(5)
{ "_id" : ObjectId("52b95bc791af8553649391d2"), "x" : 10 }
{ "_id" : ObjectId("52b95bc791af8553649391d3"), "x" : 11 }
{ "_id" : ObjectId("52b95bc791af8553649391d4"), "x" : 12 }
{ "_id" : ObjectId("52b95bc791af8553649391d5"), "x" : 13 }
{ "_id" : ObjectId("52b95bc791af8553649391d6"), "x" : 14 }
#sort
> db.c.find().skip(10).limit(6).sort({"x":-1})
{ "_id" : ObjectId("52b95bc791af855364939221"), "x" : 89 }
{ "_id" : ObjectId("52b95bc791af855364939220"), "x" : 88 }
{ "_id" : ObjectId("52b95bc791af85536493921f"), "x" : 87 }
{ "_id" : ObjectId("52b95bc791af85536493921e"), "x" : 86 }
{ "_id" : ObjectId("52b95bc791af85536493921d"), "x" : 85 }
{ "_id" : ObjectId("52b95bc791af85536493921c"), "x" : 84 }
随机抽取文档
db.people.insert({"name" : "joe", "random" : Math.random()})
db.people.insert({"name" : "john", "random" : Math.random()})
db.people.insert({"name" : "jim", "random" : Math.random()})
db.people.find()
var random = Math.random()
result = db.people.findOne({"random" : {"$gt" : random}})
索引
可以在任意列上建立索引,使用索引可以加快查询,但同时会降低修改,插入等的性能,内嵌文档照样可以建立使用索引。
> db.people.insert({"name" : "joe", "random" : Math.random()})
> db.people.insert({"name" : "john", "random" : Math.random()})
> db.people.insert({"name" : "jim", "random" : Math.random()})
> db.people.insert({ "username" : "smith", "age" : 48, "user_id" : 0 })
> db.people.insert({ "username" : "smith", "age" : 30, "user_id" : 1 })
> db.people.insert({ "username" : "john", "age" : 36, "user_id" : 2 })
> db.people.insert({ "username" : "john", "age" : 18, "user_id" : 3 })
> db.people.insert({ "username" : "joe", "age" : 36, "user_id" : 4 })
> db.people.insert({ "username" : "john", "age" : 7, "user_id" : 5 })
> db.people.insert({ "username" : "simon", "age" : 3, "user_id" : 6 })
> db.people.insert({ "username" : "joe", "age" : 27, "user_id" : 7 })
> db.people.insert({ "username" : "jacob", "age" : 17, "user_id" : 8 })
> db.people.insert({ "username" : "sally", "age" : 52, "user_id" : 9 })
> db.people.insert({ "username" : "simon", "age" : 59, "user_id" : 10 })
> db.people.find();
{ "_id" : ObjectId("52b9674691af855364939232"), "name" : "joe", "random" : 0.11840517622932434 }
{ "_id" : ObjectId("52b9674691af855364939233"), "name" : "john", "random" : 0.24741847155078767 }
{ "_id" : ObjectId("52b9674691af855364939234"), "name" : "jim", "random" : 0.5261716402139863 }
{ "_id" : ObjectId("52b9674691af855364939235"), "username" : "smith", "age" : 48, "user_id" : 0 }
{ "_id" : ObjectId("52b9674691af855364939236"), "username" : "smith", "age" : 30, "user_id" : 1 }
{ "_id" : ObjectId("52b9674691af855364939237"), "username" : "john", "age" : 36, "user_id" : 2 }
{ "_id" : ObjectId("52b9674691af855364939238"), "username" : "john", "age" : 18, "user_id" : 3 }
{ "_id" : ObjectId("52b9674691af855364939239"), "username" : "joe", "age" : 36, "user_id" : 4 }
{ "_id" : ObjectId("52b9674691af85536493923a"), "username" : "john", "age" : 7, "user_id" : 5 }
{ "_id" : ObjectId("52b9674691af85536493923b"), "username" : "simon", "age" : 3, "user_id" : 6 }
{ "_id" : ObjectId("52b9674691af85536493923c"), "username" : "joe", "age" : 27, "user_id" : 7 }
{ "_id" : ObjectId("52b9674691af85536493923d"), "username" : "jacob", "age" : 17, "user_id" : 8 }
{ "_id" : ObjectId("52b9674791af85536493923e"), "username" : "sally", "age" : 52, "user_id" : 9 }
{ "_id" : ObjectId("52b9674891af85536493923f"), "username" : "simon", "age" : 59, "user_id" : 10 }
#建立索引
> db.people.ensureIndex({"username" : 1})
> db.people.ensureIndex({"username" : 1,"age":-1}) ##1是正序 -1是反序
#用explain()查看索引使用
> db.people.find().explain();
{
"cursor" : "BasicCursor", #没有使用索引
"nscanned" : 14, #扫描行数
"nscannedObjects" : 14,
"n" : 14, #返回行数
"millis" : 0, #时间
"nYields" : 0,
"nChunkSkips" : 0,
"isMultiKey" : false,
"indexOnly" : false,
"indexBounds" : {
}
}
> db.people.find({username:"john"}).explain();
{
"cursor" : "BtreeCursor username_1", #使用索引
"nscanned" : 3,
"nscannedObjects" : 3,
"n" : 3,
"millis" : 1,
"nYields" : 0,
"nChunkSkips" : 0,
"isMultiKey" : false,
"indexOnly" : false,
"indexBounds" : {
"username" : [
[
"john",
"john"
]
]
}
}
#观看有哪些索引
> db.system.indexes.find()
{ "v" : 1, "key" : { "_id" : 1 }, "ns" : "test.foo", "name" : "_id_" }
{ "v" : 1, "key" : { "_id" : 1 }, "ns" : "test.c", "name" : "_id_" }
{ "v" : 1, "key" : { "_id" : 1 }, "ns" : "test.people", "name" : "_id_" }
{ "v" : 1, "key" : { "username" : 1 }, "ns" : "test.people", "name" : "username_1" }
{ "v" : 1, "key" : { "username" : 1, "age" : -1 }, "ns" : "test.people", "name" : "username_1_age_-1" }
#更多例子
// 创建子文档索引
db.things.ensureIndex({"user.Name": -1});
// 重建索引
db.things.reIndex();
// 删除集合中的所有索引
db.things.dropIndexes();
// 删除指定键的索引
db.things.dropIndex({x: 1,y: -1});
// 使用command删除指定键的索引
db.runCommand({dropIndexes:'foo',index : { y: 1 }});
// 使用command删除所有索引 db.runCommand({dropIndexes:'foo',index : "*"});
// 创建唯一索引,同时这也
// 是一个符合唯一索引
db.things.ensureIndex({'firstName': 1,'lastName': 1
}, {
// 指定为唯一索引
'unique': true,
// 删除重复记录
'dropDups': true
});
聚合操作
> db.people.count(); #count
14
> db.people.find();
{ "_id" : ObjectId("52b9674691af855364939232"), "name" : "joe", "random" : 0.11840517622932434 }
{ "_id" : ObjectId("52b9674691af855364939233"), "name" : "john", "random" : 0.24741847155078767 }
{ "_id" : ObjectId("52b9674691af855364939234"), "name" : "jim", "random" : 0.5261716402139863 }
{ "_id" : ObjectId("52b9674691af855364939235"), "username" : "smith", "age" : 48, "user_id" : 0 }
{ "_id" : ObjectId("52b9674691af855364939236"), "username" : "smith", "age" : 30, "user_id" : 1 }
{ "_id" : ObjectId("52b9674691af855364939237"), "username" : "john", "age" : 36, "user_id" : 2 }
{ "_id" : ObjectId("52b9674691af855364939238"), "username" : "john", "age" : 18, "user_id" : 3 }
{ "_id" : ObjectId("52b9674691af855364939239"), "username" : "joe", "age" : 36, "user_id" : 4 }
{ "_id" : ObjectId("52b9674691af85536493923a"), "username" : "john", "age" : 7, "user_id" : 5 }
{ "_id" : ObjectId("52b9674691af85536493923b"), "username" : "simon", "age" : 3, "user_id" : 6 }
{ "_id" : ObjectId("52b9674691af85536493923c"), "username" : "joe", "age" : 27, "user_id" : 7 }
{ "_id" : ObjectId("52b9674691af85536493923d"), "username" : "jacob", "age" : 17, "user_id" : 8 }
{ "_id" : ObjectId("52b9674791af85536493923e"), "username" : "sally", "age" : 52, "user_id" : 9 }
{ "_id" : ObjectId("52b9674891af85536493923f"), "username" : "simon", "age" : 59, "user_id" : 10 }
> db.runCommand({"distinct" : "people", "key" : "age"}) #distinct
{
"values" : [
null,
17,
36,
27,
18,
7,
52,
59,
3,
48,
30
],
"stats" : {
"n" : 14,
"nscanned" : 14,
"nscannedObjects" : 0,
"timems" : 0,
"cursor" : "BtreeCursor username_1_age_-1"
},
"ok" : 1
}
> db.runCommand({"distinct" : "people", "key" : "username"}) #distinct
{
"values" : [
null,
"jacob",
"joe",
"john",
"sally",
"simon",
"smith"
],
"stats" : {
"n" : 14,
"nscanned" : 14,
"nscannedObjects" : 0,
"timems" : 0,
"cursor" : "BtreeCursor username_1"
},
"ok" : 1
}
##聚合:group
> db.people.group({
... "key":{"username":true},
... "initial": {"csum": 0 },
... "reduce":function(obj, prev)
... {
... prev.csum += obj.age;
... }
... })
[
{
"username" : null,
"csum" : NaN
},
{
"username" : "smith",
"csum" : 78
},
{
"username" : "john",
"csum" : 61
},
{
"username" : "joe",
"csum" : 63
},
{
"username" : "simon",
"csum" : 62
},
{
"username" : "jacob",
"csum" : 17
},
{
"username" : "sally",
"csum" : 52
}
]
MapReduce
与Hadoop的Map-Reduce神似,能完成count、distinct、group所能做的一切事情。
例子:寻找集合中所有的键
map = function() {
for (var key in this) {
emit(key, {count : 1});
}};
reduce = function(key, emits) {
total = 0;
for (var i in emits) {
total += emits[i].count;
}
return {"count" : total};
};
db.runCommand({"mapreduce" : "people", "map" : map, "reduce" : reduce,"out":"result"});
db.result.find();