Jer*_*rey 2 mongodb mongodb-query
我正在尝试对字段执行 mongodb 正则表达式查询。我希望查询在找到一个匹配项时优先考虑完整匹配项,然后再优先考虑部分匹配项。
例如,如果我有一个充满以下条目的数据库。
{
"username": "patrick"
},
{
"username": "robert"
},
{
"username": "patrice"
},
{
"username": "pat"
},
{
"username": "patter"
},
{
"username": "john_patrick"
}
Run Code Online (Sandbox Code Playgroud)
我查询用户名“pat”,我想首先返回直接匹配的结果,然后是部分匹配。因此结果将排序为 ['pat', 'patrick', 'patrice', 'patter', 'john_patrick']。
是否可以单独使用 mongo 查询来完成此操作?如果是这样,有人可以向我指出详细说明如何实现它的资源吗?
这是我尝试用来执行此操作的查询。
db.accounts.aggregate({ $match :
{
$or : [
{ "usernameLowercase" : "pat" },
{ "usernameLowercase" : { $regex : "pat" } }
]
} })
Run Code Online (Sandbox Code Playgroud)
鉴于您的精确示例,这可以通过以下方式完成 - 如果您的现实世界场景稍微复杂一点,您可能会遇到问题:
db.accounts.aggregate([{
$match: {
"username": /pat/i // find all documents that somehow match "pat" in a case-insensitive fashion
}
}, {
$addFields: {
"exact": {
$eq: [ "$username", "pat" ] // add a field that indicates if a document matches exactly
},
"startswith": {
$eq: [ { $substr: [ "$username", 0, 3 ] }, "pat" ] // add a field that indicates if a document matches at the start
}
}
}, {
$sort: {
"exact": -1, // sort by our primary temporary field
"startswith": -1 // sort by our seconday temporary
}
}, {
$project: {
"exact": 0, // get rid of the "exact" field,
"startswith": 0 // same for "startswith"
}
}])
Run Code Online (Sandbox Code Playgroud)
另一种方法是使用$facet
它,它可以通过启用更复杂的场景但速度更慢来证明更强大(不过,这里的一些人会因为这个提案而讨厌我):
db.accounts.aggregate([{
$facet: { // run two pipelines against all documents
"exact": [{ // this one will capture all exact matches
$match: {
"username": "pat"
}
}],
"others": [{ // this one will capture all others
$match: {
"username": { $ne: "pat", $regex: /pat/i }
}
}]
}
}, {
$project: {
"result": { // merge the two arrays
$concatArrays: [ "$exact", "$others" ]
}
}
}, {
$unwind: "$result" // flatten the resulting array into separate documents
}, {
$replaceRoot: { // restore the original document structure
"newRoot": "$result"
}
}])
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
1616 次 |
最近记录: |