我遇到了需要在字符串中匹配完全标记在MongoDB中进行$ text $搜索的情况。我想我可以通过创建没有默认语言的文本索引来解决这个问题,并通过用\"token\"
包装每个标记来执行查询,如documentation中所述。所以我用这种方式创建了索引:
db.collection.createIndex({"denom": "text"}, {"default_language": "none"})
我必须执行的查询是
db.collection.find( {"$text": {"$search": "\"consorzio\" \"la\""}}, {"denom": 1} )
我期望的结果是所有包含令牌"consorzio"
和"la"
的文档,但此查询会匹配其标记包含字符串“la”的文档,每个令牌内的“consorzio”
例如,上面的查询返回我期望的以下denom值:
有人可以解决这个问题吗?我希望问题很清楚。
非常感谢你。
答案 0 :(得分:0)
Mongodb报告了此issue的错误。精确加工不起作用。
你可以看一下加工得分:
db.docs.find({$text: {$search: "\"consorzio\" \"la\""}},
{score: { $meta: "textScore" }, "_id": 0})
{ "t" : "CONSORZIO LA* CASCINA OK", "score" : 1.25 }
{ "t" : "LA RADA CONSORZIO OK", "score" : 1.25 }
{ "t" : "GESCO CONSORZIO AGRICOLA WRONG", "score" : 0.625 }
解决方案应该是考虑到最高分......
答案 1 :(得分:0)
费尔南多(Fernando),您实际上错了,它与GESCO CONSORZIO AGRICOLA WRONG
匹配,但仅与您搜索的一个单词(令牌)匹配,consorzio
而不是la
。
在文本搜索中,
textScore
大于1时 匹配查询的所有标记。
例如这是一个商店集合
db.stores.insert(
[
{ _id: 1, name: "Java Hut", description: "Coffee and cakes" },
{ _id: 2, name: "Burger Buns", description: "Gourmet hamburgers" },
{ _id: 3, name: "Coffee Java Shop", description: "Just coffee" },
{ _id: 4, name: "Clothes Clothes Clothes", description: "Discount clothing" },
{ _id: 5, name: "Java Shopping", description: "Indonesian goods" },
{ _id: 6, name: "Java Hut", description: "Coffee and cakes" }
]
)
索引
db.stores.createIndex( { name: "text" } )
现在,如果我查询
db.stores.find({
$text: {
$search: "Java Shop"
}
}, {
score: {
$meta: "textScore"
}
}).sort({
score: {
$meta: "textScore"
},
_id: -1
})
它将匹配令牌并且结果为
/* 1 */
{
"_id" : 6.0,
"name" : "Java Shopping",
"description" : "Indonesian goods",
"score" : 1.5
}
/* 2 */
{
"_id" : 5.0,
"name" : "Java Shopping",
"description" : "Indonesian goods",
"score" : 1.5
}
/* 3 */
{
"_id" : 3.0,
"name" : "Java Coffee Shop",
"description" : "Just coffee",
"score" : 1.33333333333333
}
/* 4 */
{
"_id" : 1.0,
"name" : "Java Hut",
"description" : "Coffee and cakes",
"score" : 0.75
}
在这里您可以看到前三个文档与所有标记匹配,这就是为什么score
大于1,而最后一个文档score
小于1的原因,因为它仅匹配一个标记。
现在,在分数大于1的情况下,您还可以获得与所有令牌匹配的最佳文档。为此,我们需要使用MongoDB Aggregation。
db.stores.aggregate([
{
"$match": {
"$text": {
"$search": "Java Shop"
}
}
},
{
"$addFields": {
"score": {
"$meta": "textScore"
}
}
},
{
"$match": {
"score": { "$gt": 1.0 }
}
},
{
"$sort": {
"score": -1, _id: -1
}
},
{
"$limit": 1
}
])
&这是结果
/* 1 */
{
"_id" : 6.0,
"name" : "Java Shopping",
"description" : "Indonesian goods",
"score" : 1.5
}