[[bool-query]] === Combining Queries
In <bool filter to combine
multiple filter clauses with and, or, and not logic. In query land, the
bool query does a similar job but with one important difference.
Filters make a binary decision: should this document be included in the results list or not? Queries, however, are more subtle. They decide not only whether to include a document, but also how relevant that document is.
Like the filter equivalent, the bool query accepts((("bool query"))) multiple query clauses
under the must, must_not, and should parameters. For instance:
GET /my_index/my_type/_search { "query": { "bool": { "must": { "match": { "title": "quick" }}, "must_not": { "match": { "title": "lazy" }}, "should": [ { "match": { "title": "brown" }}, { "match": { "title": "dog" }} ] } }
// SENSE: 100_Full_Text_Search/15_Bool_query.json
The results from the preceding query include any document whose title field
contains the term quick, except for those that also contain lazy. So
far, this is pretty similar to how the bool filter works.
The difference comes in with the two should clauses, which say that: a document
is not required to contain ((("should clause", "in bool queries")))either brown or dog, but if it does, then
it should be considered more relevant:
{ "hits": [ { "_id": "3", "_score": 0.70134366, <1> "_source": { "title": "The quick brown fox jumps over the quick dog" } }, { "_id": "1", "_score": 0.3312608, "_source": { "title": "The quick brown fox" } } ]
<1> Document 3 scores higher because it contains both brown and dog.
==== Score Calculation
The bool query calculates((("relevance scores", "calculation in bool queries")))((("bool query", "score calculation"))) the relevance _score for each document by adding
together the _score from all of the matching must and should clauses,
and then dividing by the total number of must and should clauses.
The must_not clauses do not affect ((("must_not clause", "in bool queries")))the score; their only purpose is to
exclude documents that might otherwise have been included.
==== Controlling Precision
All the must clauses must match, and all the must_not clauses must not
match, but how many should clauses((("bool query", "controlling precision")))((("full text search", "combining queries", "controlling precision")))((("precision", "controlling for bool query"))) should match? By default, none of the should clauses are required to match, with one
exception: if there are no must clauses, then at least one should clause
must match.
Just as we can control the <should clauses need to match by using the
minimum_should_match parameter,((("minimum_should_match parameter", "in bool queries"))) either as an absolute number or as a
percentage:
GET /my_index/my_type/_search { "query": { "bool": { "should": [ { "match": { "title": "brown" }}, { "match": { "title": "fox" }}, { "match": { "title": "dog" }} ], "minimum_should_match": 2 <1> } }
// SENSE: 100_Full_Text_Search/15_Bool_query.json
<1> This could also be expressed as a percentage.
The results would include only documents whose title field contains "brown"
AND "fox", "brown" AND "dog", or "fox" AND "dog". If a document contains
all three, it would be considered more relevant than those that contain
just two of the three.