更多类似内容
定义
行为
当您运行 moreLikeThis
查询时,Atlas Search 会执行以下操作:
根据您在操作符的
like
选项中指定的输入文档,提取有限数量的最具代表性的术语。创建析取 (OR) 查询,根据最具代表性的术语查找相似文档并返回结果。
moreLikeThis
操作符使用您在索引配置中指定的 分析器来搜索相似文档。如果在索引定义中省略了分析器,则 moreLikeThis
操作符将使用默认的标准分析器。如果指定了多个分析器,则 moreLikeThis
操作符将通过每个分析器运行输入文本、搜索并返回所有分析器的结果。
要查看Atlas Search为查找相似文档而构建的析取(OR),请将explain与moreLikeThis
操作符查询一起使用。
使用
在运行 moreLikeThis
运算符查询之前,我们建议您检索一个或多个输入文档。要检索输入文档,可以执行下列操作之一:
运行查询,例如 find() 或另一个 MQL 查询来查找 BSON 文档。
运行任何返回 BSON 文档的聚合管道。
在应用程序中使用任何其他来源的文档。
识别输入文档后,您就可以将它们传递给 moreLikeThis
操作符。
当您运行 moreLikeThis
运算符查询时,Atlas Search 将在查询结果中返回原始输入文档。要从查询结果中忽略输入文档,在复合运算符查询中使用 moreLikeThis
运算符,并在 MustNot 子句中使用 equals
运算符根据 _id
排除输入文档。
语法
moreLikeThis
通过以下语法实现:
{ "$search": { "index": index name, // optional, defaults to "default" "moreLikeThis": { "like": [ { <"field-name">: <"field-value">, ... }, ... ], "score": <options> } } }
选项
moreLikeThis
使用以下选项来构造查询:
字段 | 类型 | 说明 | 必要性 |
---|---|---|---|
| 一个 BSON 文档或文档数组 | Atlas Search 用来提取代表性词语进行查询的一个或多个 BSON 文档。 | 必需 |
| 对象 | 分配给匹配搜索结果的分数。您可以使用以下选项修改默认分数:
有关在查询中使用 当您查询数组中的值时,Atlas Search 不会根据与查询匹配的数组内的值数量更改匹配结果的分数。无论数组内有多少个匹配项,分数都将与单个匹配项相同。 | Optional |
限制
您不能使用 moreLikeThis
运算符查询非字符串值。要搜索非字符串值,可以将 moreLikeThis
查询与复合运算符查询中的接近、范围或任何其他运算符相结合。
您不能在 embeddedDocument 运算中使用 moreLikeThis
运算符来查询数组中的文档。
示例
这些示例使用 sample_mflix
数据库中的 movies
集合。本部分中的每个示例都使用不同的索引定义来演示运算符的不同功能。
在集群上运行示例查询前,在 Atlas 集群上加载示例数据,然后创建建议的索引。要了解使用用户界面、API 或 CLI 创建 Atlas Search 索引的更多信息,请参阅创建 Atlas Search 索引。索引定义使用名称 default
。
如果将索引命名为 default
,则在使用 $search 管道阶段时无需指定 index
参数。如果您为索引指定了自定义名称,则必须在 index
参数中指定此名称。
示例 1:具有多个字段的单个文档
以下示例使用 moreLikeThis
运算符查找与多个字段值相似的文档。在本示例中,索引定义包含动态映射,用于动态索引集合中所有可动态索引的字段类型。sample_mflix.movies
集合的索引定义应与以下内容相似。
{ "mappings": { "dynamic": true } }
例子
以下查询搜索与输入电影标题“教父”和输入电影类型“动作片”相似的电影。它包括一个 $limit
阶段,用于将输出限制为 5
个结果,以及一个 $project
阶段,用于排除除 title
、released
和 genres
之外的所有字段。
1 db.movies.aggregate([ 2 { 3 "$search": { 4 moreLikeThis: { 5 like: 6 { 7 "title": "The Godfather", 8 "genres": "action" 9 } 10 } 11 } 12 }, 13 { "$limit": 5}, 14 { 15 $project: { 16 "_id": 0, 17 "title": 1, 18 "released": 1, 19 "genres": 1 20 } 21 } 22 ])
[ { genres: [ 'Comedy', 'Drama', 'Romance' ], title: 'Godfather' }, { genres: [ 'Crime', 'Drama' ], title: 'The Godfather', released: ISODate("1972-03-24T00:00:00.000Z") }, { genres: [ 'Crime', 'Drama' ], title: 'The Godfather: Part II', released: ISODate("1974-12-20T00:00:00.000Z") }, { genres: [ 'Crime', 'Drama' ], title: 'The Godfather: Part III', released: ISODate("1990-12-26T00:00:00.000Z") }, { genres: [ 'Action' ], title: 'The Defender', released: ISODate("1994-07-28T00:00:00.000Z") } ]
Atlas Search 结果包含与输入电影标题“教父”和输入电影类型“动作片”相似的电影。
示例 2:在结果中排除的输入文档
下面的示例使用 find()
识别输入文档,然后使用 moreLikeThis
运算符查找类似文档。在此示例中,索引定义使用静态映射仅为 title
、genres
和 _id
字段编制索引。
1 { 2 "mappings": { 3 "dynamic": false, 4 "fields": { 5 "title": { 6 "type": "string" 7 }, 8 "genres": { 9 "type": "string" 10 }, 11 "_id": { 12 "type": "objectId" 13 } 14 } 15 } 16 }
例子
以下 find()
查询查找标题为“教父”的电影并将结果存储在 movie
中。它指定结果应仅包含匹配文档的 title
和 genres
字段。请注意,默认情况下,find
()
命令始终返回 _id
字段,该字段的值在您的集群上可能有所不同。
movie = db.movies.find( { title: "The Godfather" }, { genres: 1, title: 1} ).toArray()
[ { _id: ObjectId("573a1396f29313caabce4a9a"), genres: [ 'Crime', 'Drama' ], title: 'The Godfather' } ]
以下查询是使用复合运算符和 moreLikeThis
运算符查询 title
和 genres
字段,并使用等于运算符排除使用以下子句的输入文档:
must
子句用于查询与movie
中存储的电影相似的电影。mustNot
子句是根据其_id
值从结果中排除输入文档。请注意,查询中使用的_id
值与前面的find()
查询结果中的_id
值相符。
查询限制输出 5
个结果。查询使用 $project
阶段,将 _id
、title
、released
和 genres
字段包含在结果中。
注意
在运行此查询之前,将第 13 行的 _id
字段的值替换为查询结果中 _id
字段的值。
1 db.movies.aggregate([ 2 { 3 "$search": { 4 "compound":{ 5 "must":[{ 6 "moreLikeThis": { 7 "like": movie 8 } 9 }], 10 "mustNot":[{ 11 "equals": { 12 "path": "_id", 13 "value": ObjectId ("573a1396f29313caabce4a9a") 14 } 15 }] 16 } 17 } 18 }, 19 {"$limit": 5}, 20 { 21 "$project": { 22 "_id": 1, 23 "title": 1, 24 "released": 1, 25 "genres": 1 26 } 27 } 28 ])
[ { _id: ObjectId("573a13acf29313caabd27afc"), genres: [ 'Comedy', 'Drama', 'Romance' ], title: 'Godfather' }, { _id: ObjectId("573a1396f29313caabce557f"), genres: [ 'Crime', 'Drama' ], title: 'The Godfather: Part II', released: ISODate("1974-12-20T00:00:00.000Z") }, { _id: ObjectId("573a1398f29313caabcebf7b"), genres: [ 'Crime', 'Drama' ], title: 'The Godfather: Part III', released: ISODate("1990-12-26T00:00:00.000Z") }, { _id: ObjectId("573a1399f29313caabceed8d"), genres: [ 'Action' ], title: 'The Defender', released: ISODate("1994-07-28T00:00:00.000Z") }, { _id: ObjectId("573a139af29313caabcef2a0"), genres: [ 'Action' ], title: 'The Enforcer', released: ISODate("1995-03-02T00:00:00.000Z") } ]
Atlas Search 结果包括与 action
类型中的查询术语 The Godfather
相似的文档。但是,结果不包括被其 _id
排除的文档,即 ObjectId("573a1396f29313caabce4a9a")
。
示例 3:多个分析器
以下示例使用 find()
识别输入文档,然后使用 moreLikeThis
运算符查找相似文档。在此示例中,索引定义通过静态映射以使用不同的分析器对 sample_mflix.movies
集合中的字段进行索引。索引定义:
在
_id
、title
和genres
字段上配置索引。使用
lucene.standard
分析器和名为keywordAnalyzer
、使用lucene.keyword
分析器的备用分析器分析title
字段。使用
lucene.english
分析器分析和搜索字段。
1 { 2 "mappings": { 3 "dynamic": false, 4 "fields": { 5 "title": { 6 "type": "string", 7 "analyzer": "lucene.standard", 8 "multi": { 9 "keywordAnalyzer": { 10 "type": "string", 11 "analyzer": "lucene.keyword" 12 } 13 } 14 }, 15 "genres": { 16 "type": "string" 17 }, 18 "_id": { 19 "type": "objectId" 20 } 21 } 22 }, 23 "analyzer": "lucene.english" 24 }
例子
以下 find()
查询检索标题为“爱丽丝梦游仙境”的电影并将结果存储在 movie
中。它指定结果应仅包含匹配文档的 title
和 genres
字段。请注意,默认情况下,find()
命令始终返回 _id
字段,该字段的值在您的集群上可能有所不同。
movie = db.movies.find( { title: "Alice in Wonderland" }, { genres: 1, title: 1} ).toArray
[ { _id: ObjectId("573a1394f29313caabcde9ef"), plot: 'Alice stumbles into the world of Wonderland. Will she get home? Not if the Queen of Hearts has her way.', title: 'Alice in Wonderland' }, { _id: ObjectId("573a1398f29313caabce963d"), plot: 'Alice is in Looking Glass land, where she meets many Looking Glass creatures and attempts to avoid the Jabberwocky, a monster that appears due to her being afraid.', title: 'Alice in Wonderland' }, { _id: ObjectId("573a1398f29313caabce9644"), plot: 'Alice is in Looking Glass land, where she meets many Looking Glass creatures and attempts to avoid the Jabberwocky, a monster that appears due to her being afraid.', title: 'Alice in Wonderland' }, { _id: ObjectId("573a139df29313caabcfb504"), plot: `The wizards behind The Odyssey (1997) and Merlin (1998) combine Lewis Carroll's "Alice in Wonderland" and "Through the Looking Glass" into a two-hour special that just gets curiouser and curiouser.`, title: 'Alice in Wonderland' }, { _id: ObjectId("573a13bdf29313caabd5933b"), plot: "Nineteen-year-old Alice returns to the magical world from her childhood adventure, where she reunites with her old friends and learns of her true destiny: to end the Red Queen's reign of terror.", title: 'Alice in Wonderland' } ]
以下示例使用复合操作符,通过以下子句查询 title
和 genres
字段:
should
子句使用moreLikeThis
操作符,搜索与movie
中的文档类似的文档。请注意,title
字段同时使用lucene.standard
和lucene.keyword
分析器进行分析。mustNot
子句指定,其中一个输入文档(用其_id
值来指定)得包含在结果中。
查询将结果列表限制为 10
个文档。查询使用 $project
阶段,将 _id
、title
和 genres
字段包含在结果中。
例子
1 db.movies.aggregate([ 2 { 3 $search: { 4 "compound": { 5 "should": [{ 6 "moreLikeThis": { 7 "like": movie 8 } 9 }], 10 "mustNot": [ 11 { 12 "equals": { 13 "path": "_id", 14 "value": ObjectId ("573a1394f29313caabcde9ef") 15 } 16 }] 17 } 18 } 19 }, 20 { $limit: 10 }, 21 { 22 $project: { 23 "title": 1, 24 "genres": 1, 25 "_id": 1 26 } 27 } 28 ])
[ { _id: ObjectId("573a1398f29313caabce963d"), genres: [ 'Adventure', 'Family', 'Fantasy' ], title: 'Alice in Wonderland' }, { _id: ObjectId("573a1398f29313caabce9644"), genres: [ 'Adventure', 'Family', 'Fantasy' ], title: 'Alice in Wonderland' }, { _id: ObjectId("573a139df29313caabcfb504"), genres: [ 'Adventure', 'Comedy', 'Family' ], title: 'Alice in Wonderland' }, { _id: ObjectId("573a13bdf29313caabd5933b"), genres: [ 'Adventure', 'Family', 'Fantasy' ], title: 'Alice in Wonderland' }, { _id: ObjectId("573a1396f29313caabce3e7e"), genres: [ 'Comedy', 'Drama' ], title: 'Alex in Wonderland' }, { _id: ObjectId("573a13bdf29313caabd5a44b"), genres: [ 'Drama' ], title: 'Phoebe in Wonderland' }, { _id: ObjectId("573a139af29313caabcf0e23"), genres: [ 'Documentary' ], title: 'Wonderland' }, { _id: ObjectId("573a139ef29313caabcfcebc"), genres: [ 'Drama' ], title: 'Wonderland' }, { _id: ObjectId("573a13a0f29313caabd03dab"), genres: [ 'Drama' ], title: 'Wonderland' }, { _id: ObjectId("573a13abf29313caabd2372a"), genres: [ 'Crime', 'Drama', 'Mystery' ], title: 'Wonderland' } ]
以下查询将解释与前面的查询一起使用,以显示 Atlas Search 为查找相似文档而构建的析取 (OR)。
db.movies.explain("queryPlanner").aggregate([ { $search: { "compound": { "should": [{ "moreLikeThis": { "like": [{ "title": "Alice in Wonderland" }] } }], "mustNot": [ { "equals": { "path": "_id", "value": ObjectId ("573a1394f29313caabcde9ef") } }] } } }, { $limit: 10 }, { $project: { "title": 1, "genres": 1, "_id": 1 } } ])
{ explainVersion: '1', stages: [ { '$_internalSearchMongotRemote': { mongotQuery: { compound: { should: [ { moreLikeThis: { like: [ { title: 'Alice in Wonderland' } ] } } ], mustNot: [ { equals: { path: '_id', value: ObjectId("573a1394f29313caabcde9ef") } } ] } }, explain: { type: 'BooleanQuery', args: { must: [], mustNot: [ { path: 'compound.mustNot', type: 'ConstantScoreQuery', args: { query: { type: 'TermQuery', args: { path: '_id', value: '[57 3a 13 94 f2 93 13 ca ab cd e9 ef]' } } } } ], should: [ { path: 'compound.should', type: 'BooleanQuery', args: { must: [], mustNot: [], should: [ { type: 'TermQuery', args: { path: 'title', value: 'in' } }, { type: 'TermQuery', args: { path: 'title.keywordAnalyzer', value: 'Alice in Wonderland' } }, { type: 'TermQuery', args: { path: 'title', value: 'wonderland' } }, { type: 'TermQuery', args: { path: 'title', value: 'alice' } } ], filter: [], minimumShouldMatch: 0 } } ], filter: [], minimumShouldMatch: 0 } } } }, { '$_internalSearchIdLookup': {} }, { '$limit': Long("10") }, { '$project': { _id: true, title: true, genres: true } } ], serverInfo: { ... }, serverParameters: { ... }, command: { aggregate: 'movies', pipeline: [ { '$search': { compound: { should: [ { moreLikeThis: { like: [ { title: 'Alice in Wonderland' } ] } } ], mustNot: [ { equals: { path: '_id', value: ObjectId("573a1394f29313caabcde9ef") } } ] } } }, { '$limit': 10 }, { '$project': { title: 1, genres: 1, _id: 1 } } ], cursor: {}, '$db': 'sample_mflix' }, ok: 1, '$clusterTime': { clusterTime: Timestamp({ t: 1659133479, i: 1 }), signature: { hash: Binary(Buffer.from("865d9ef1187ae1a74c4a0da1e29882aebcf2be7c", "hex"), 0), keyId: Long("7123262728533180420") } }, operationTime: Timestamp({ t: 1659133479, i: 1 }) }