一.通过查询获取数据
在深入讨论查询之前,首先来了解一下查询返回的结果——游标(cursor)对象。上一篇文章中我们使用的是最简单的find() 查询方法,它会返回结果集中的所有对象,稍后将讨论如何查询特定数据集。
为了看到集合中的所用元素,我们需要使用到find ()函数返回的cursor对象。让我们来重复上一篇文章中使用的find()函数,不过这次我们使用的是find()返回的cursor对象,然后使用while循环遍历cursor对象输出:
> var cursor = db.things.find(); > while (cursor.hasNext()) printjson(cursor.next());{ " _id " : ObjectId( " 4e205546b3fcd89b00572c31 " ), " name " : " mongo " }{ " _id " : ObjectId( " 4e20554fb3fcd89b00572c32 " ), " x " : 3 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c33 " ), " x " : 4 , " j " : 1 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c34 " ), " x " : 4 , " j " : 2 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c35 " ), " x " : 4 , " j " : 3 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c36 " ), " x " : 4 , " j " : 4 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c37 " ), " x " : 4 , " j " : 5 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c38 " ), " x " : 4 , " j " : 6 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c39 " ), " x " : 4 , " j " : 7 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3a " ), " x " : 4 , " j " : 8 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3b " ), " x " : 4 , " j " : 9 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3c " ), " x " : 4 , " j " : 10 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3d " ), " x " : 4 , " j " : 11 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3e " ), " x " : 4 , " j " : 12 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3f " ), " x " : 4 , " j " : 13 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c40 " ), " x " : 4 , " j " : 14 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c41 " ), " x " : 4 , " j " : 15 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c42 " ), " x " : 4 , " j " : 16 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c43 " ), " x " : 4 , " j " : 17 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c44 " ), " x " : 4 , " j " : 18 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c45 " ), " x " : 4 , " j " : 19 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c46 " ), " x " : 4 , " j " : 20 } 语法有点像C#,hasNext()函数判断是否有记录。next()函数返回下一条记录。使用内置的printjson()方法能够将结果输出为json格式。
我们也可以直接在返回的cursor对象上使用forEach()函数而不是while循环来达到同样的效果:
> db.things.find().forEach(printjson);{ " _id " : ObjectId( " 4e205546b3fcd89b00572c31 " ), " name " : " mongo " }{ " _id " : ObjectId( " 4e20554fb3fcd89b00572c32 " ), " x " : 3 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c33 " ), " x " : 4 , " j " : 1 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c34 " ), " x " : 4 , " j " : 2 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c35 " ), " x " : 4 , " j " : 3 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c36 " ), " x " : 4 , " j " : 4 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c37 " ), " x " : 4 , " j " : 5 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c38 " ), " x " : 4 , " j " : 6 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c39 " ), " x " : 4 , " j " : 7 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3a " ), " x " : 4 , " j " : 8 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3b " ), " x " : 4 , " j " : 9 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3c " ), " x " : 4 , " j " : 10 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3d " ), " x " : 4 , " j " : 11 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3e " ), " x " : 4 , " j " : 12 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3f " ), " x " : 4 , " j " : 13 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c40 " ), " x " : 4 , " j " : 14 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c41 " ), " x " : 4 , " j " : 15 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c42 " ), " x " : 4 , " j " : 16 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c43 " ), " x " : 4 , " j " : 17 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c44 " ), " x " : 4 , " j " : 18 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c45 " ), " x " : 4 , " j " : 19 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c46 " ), " x " : 4 , " j " : 20 } 使用forEach()我们必须事先定义一个能够从游标中返回每条记录的函数,上面的printjson就是内置的函数。
在Mongodb中也可以像使用数组一样来使用游标。
> var cursor = db.things.find() > printjson(cursor[ 4 ]){ " _id " : ObjectId( " 4e205693b3fcd89b00572c35 " ), " x " : 4 , " j " : 3 } 以上命令返回记录集中的第五条数据。可见curosr中下标是从0开始的。
当使用上面语句的时候,从第一条到第四条(cursor[4])的记录会同时被加载到RAM中。对于大量数据机来说,会耗用大量内存,这是不合适的。游标应该能够通过具体的查询语句来返回任意需要的元素。
除了能够以数组的方式访问游标外,也可以将游标转换为真正的数组:
> var arr = db.things.find().toArray(); > arr[ 5 ];{ " _id " : ObjectId( " 4e205693b3fcd89b00572c36 " ), " x " : 4 , " j " : 4 } 这种以array的形式特定于mongo交互式命令行中使用,并不使用与所有的驱动中。
二.根据查询条件返回特定的记录
前面讲到了如何通过cursor对象返回记录,现在我们来看如何通过定制查询条件返回特定的记录。在mongodb中数据是以键-值对的形式存储的。在下面的例子中,给出了SQL语句和其对应的在MongoDB中查询方式。定制查询条件是MongoDB的基础。
SELECT * FROM things WHERE name = " mongo " > db.things.find({name: " mongo " }).forEach(printjson){ " _id " : ObjectId( " 4e205546b3fcd89b00572c31 " ), " name " : " mongo " }SELECT * FROM things WHERE x = 4 > db.things.find({x: 4 }).forEach(printjson){ " _id " : ObjectId( " 4e205693b3fcd89b00572c33 " ), " x " : 4 , " j " : 1 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c34 " ), " x " : 4 , " j " : 2 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c35 " ), " x " : 4 , " j " : 3 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c36 " ), " x " : 4 , " j " : 4 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c37 " ), " x " : 4 , " j " : 5 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c38 " ), " x " : 4 , " j " : 6 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c39 " ), " x " : 4 , " j " : 7 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3a " ), " x " : 4 , " j " : 8 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3b " ), " x " : 4 , " j " : 9 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3c " ), " x " : 4 , " j " : 10 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3d " ), " x " : 4 , " j " : 11 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3e " ), " x " : 4 , " j " : 12 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3f " ), " x " : 4 , " j " : 13 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c40 " ), " x " : 4 , " j " : 14 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c41 " ), " x " : 4 , " j " : 15 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c42 " ), " x " : 4 , " j " : 16 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c43 " ), " x " : 4 , " j " : 17 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c44 " ), " x " : 4 , " j " : 18 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c45 " ), " x " : 4 , " j " : 19 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c46 " ), " x " : 4 , " j " : 20 } 查询表达式中 { a:A, b:B, ... } 和SQL语句中的 "where a==A and b==B and ...”对应。
除了全部返回数据项外,我们还可以指定返回特定的列。
SELECT * FROM things WHERE x = 4 > db.things.find({x: 4 },{j: true }).forEach(printjson){ " _id " : ObjectId( " 4e205693b3fcd89b00572c33 " ), " j " : 1 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c34 " ), " j " : 2 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c35 " ), " j " : 3 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c36 " ), " j " : 4 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c37 " ), " j " : 5 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c38 " ), " j " : 6 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c39 " ), " j " : 7 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3a " ), " j " : 8 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3b " ), " j " : 9 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3c " ), " j " : 10 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3d " ), " j " : 11 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3e " ), " j " : 12 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c3f " ), " j " : 13 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c40 " ), " j " : 14 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c41 " ), " j " : 15 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c42 " ), " j " : 16 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c43 " ), " j " : 17 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c44 " ), " j " : 18 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c45 " ), " j " : 19 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c46 " ), " j " : 20 } 从中可以看出_id项是默认总是显示的。
findOne()-语法糖
为了方便,mongo交互式命令提供了findOne函数用来放回一条记录而不是cursor对象。findOne()函数的参数和find()的参数是一样的,与find函数返回cursor对象不同,findOne返回数据库集合中的第一条记录或者是null,
比如要返回一条name为mongo的记录,有很多中方式,比如今调用cursor函数的next()一次,或者是一数组的方式访问cursor并取它的第一个元素。
但是findOne提供的实现这一目的的方法简单且高效。
> printjson(db.things.findOne({name: " mongo " })){ " _id " : ObjectId( " 4e205546b3fcd89b00572c31 " ), " name " : " mongo " } 这个命令等同于find({name:”mongo”}).limit(1)
也可以通过唯一值_id来返回一条记录、
> var doc = db.things.findOne({_id:ObjectId( " 4c2209f9f3924d31102bd84a " )}); > doc{ " _id " : ObjectId( " 4c2209f9f3924d31102bd84a " ), " name " : " mongo " } 使用limite函数限制返回的记录
可以使用limite()方法来限制返回结果集的条数。例如返回记录集的前三条记录。
> db.things.find().limit( 3 ){ " _id " : ObjectId( " 4e205546b3fcd89b00572c31 " ), " name " : " mongo " }{ " _id " : ObjectId( " 4e20554fb3fcd89b00572c32 " ), " x " : 3 }{ " _id " : ObjectId( " 4e205693b3fcd89b00572c33 " ), " x " : 4 , " j " : 1 }
三.更多的帮助 如果不知道函数的用法,可以直接输入函数名(不带())来返回函数的详细用法:
> printjsonfunction (x) { print(tojson(x));}
本文简单介绍了MongoDB的查询,参考的是官方的,希望对您有帮助。