mongodb - mongo复杂查询问题

浏览:31日期:2023-06-17

问题描述

原json

{ '_id' : ObjectId('58b3a8dc96fbc7cfb8287093'), 'name' : '《地下水质量标准》', 'GBNumber' : 'GB/T 14848-93', 'dataEntryClerk' : 'handsomeboy', 'lastModified' : 'Fri Feb 27 2017 12:03:40 GMT+0800', 'contents' : [ { 'standardID' : '9527-01', 'unit' : 'mg/L', 'classifications' : [ { 'level' : 'I', 'upperLimit' : '0', 'lowerLimit' : '50'}, { 'level' : 'II', 'upperLimit' : '50', 'lowerLimit' : '150'}, { 'level' : 'III', 'upperLimit' : '150', 'lowerLimit' : '250'}, { 'level' : 'IV', 'upperLimit' : '250', 'lowerLimit' : '350'}, { 'level' : 'V', 'upperLimit' : '350', 'lowerLimit' : '-1'} ]}, { 'standardID' : '7439-89-6', 'unit' : 'mg/L', 'classifications' : [ { 'level' : 'I', 'upperLimit' : '0', 'lowerLimit' : '0.1'}, { 'level' : 'II', 'upperLimit' : '0.1', 'lowerLimit' : '0.2'}, { 'level' : 'III', 'upperLimit' : '0.2', 'lowerLimit' : '0.3'}, { 'level' : 'IV', 'upperLimit' : '0.3', 'lowerLimit' : '0.4'}, { 'level' : 'V', 'upperLimit' : '0.5', 'lowerLimit' : '-1'} ]} ]}

想查询出来的结果:

{ 'contents' : [ { 'standardID' : '9527-01', 'unit' : 'mg/L', 'classifications' : [ { 'level' : 'I', 'upperLimit' : '0', 'lowerLimit' : '50'}, { 'level' : 'II', 'upperLimit' : '50', 'lowerLimit' : '150'}, { 'level' : 'III', 'upperLimit' : '150', 'lowerLimit' : '250'}, { 'level' : 'IV', 'upperLimit' : '250', 'lowerLimit' : '350'}, { 'level' : 'V', 'upperLimit' : '350', 'lowerLimit' : '-1'} ]} ]}

请问下各位大牛db.xxx.find() 该怎么写呢

问题解答

回答1:

先提个意见:

提问题,把最小化可复现问题的例子放出来就好,你这放这么长一文档,大家看的很累。

你需要的其实是返回数组中某些特定文档,而不是整个数组。

1 如果你只需要返回数组中的一个元素

db.xxx.find( {’contents.standardID’: ’9527-01’}, {contents: {$elemMatch: {standardID: ’9527-01’}}, _id: 0})

第一行是查询条件,第二行是过滤条件。 可以看到操作符也可以用在过滤条件里面。但是这个操作符只会返回满足条件的第一个元素,并且需要2.2版本以上的MongoDB。

或者使用$下标选择符:

db.xxx.find( {’contents.standardID’: ’9527-01’}, {’contents.$’: 1, _id: 0})

上面例子中的查询条件也可以使用$elemMatch。

如果你需要返回数组中多个匹配的元素:

2 $unwind

通过把$unwind来把contents作为一个独立的文档流来进行操作,代码见@bguo的回答。但是如果你的数组很大,这会导致性能问题。

3 $filter

这是一个3.2版本中新出的操作符,用来过滤返回的内容。

db.xxx.aggregate( {$match: {’contents.standardID’: ’9527-01’}}, {$project: {contents: {$filter: { input: ’$contents’, as: ’contents’, cond: {$eq: [’$$contents.standardID’, ’9527-01’]}}},_id: 0 }})

当然你还可以使用$redact(2.6版本), 或者mapReduce()等等多种方法。

回答2:

查询条件。比如 name

db.xxx.find({'name' : '《地下水质量标准》' } ,function(err, data){ if(data){console.log(data.contents) }})回答3:

一种实现方法:利用MongoDB的Aggregate。

1、先对包含array的contents施加$unwind

2、然后利用$match,施加过滤条件

3、最后利用$project,保留所需的field

参考下方的代码

db.test1.aggregate([ {$unwind : '$contents'}, {$match : { name : '《地下水质量标准》', 'contents.standardID' : '9527-01'}}, { $project : { contents : 1 , _id : 0 }} ])

供参考。

Love MongoDB! Have Fun!

------------------------华丽的分割符--------------------------------

MongoDB中文社区线下活动缤纷,请猛戳下方:

2017华山论剑|MongoDB中文社区

三月份杭州站在即!!! 感兴趣的朋友火速报名!!!

回答4:

db.xxx.find({'contents.standardID': '9527-01'}, {contents: 1})_id字段会自动输出,就忽略吧

相关文章: