十七、组合查询
- 在单个查询中从不同的表返回类似结构的数据
- 单个表执行多个查询,按单个查询返回数据
使用UNION 创建组合查询
SELECT vend_id, prod_id, prod_price
FROM products
WHERE prod_price<=5
UNION
SELECT vend_od, prod_id, prod_price
FROM products
WHERE vend_id IN(1001,1002);
UNION
的使用有如下规则:
- 至少有两条
SELECT
语句 - 每个查询必须包含相同的列、表达式或聚集函数,顺序可以不一样
UNION
查询结果中自动去除了重复的行,如果需要显示所有的行,要使用UNION ALL
UNION
组合查询中只能在最后一条SELECT
语句之后使用一次ORDER BY
- 组合查询可以应用于不同的表
十八、全文本搜索
之前讲过的通配符和正则表达式使用上具有一些局限性:
- 要求尝试匹配所有行,耗时
- 很难控制匹配什么不匹配什么
启用全文本搜索支持
SELEC
T可以和Match
以及Against
一起执行搜索,表一般在创建时就要启用全文本搜索,接受FULLTEXT
子句,但也可以稍后指定
进行全文本搜索
SELECT note_text
FROM productnotes
WHERE Match(note_text) Against('rabbit');
上述语句中传递给Match()
的值必须与FULLTEXT()
定义中的相同,搜索不区分大小写,除非使用BINARY
方式。
全文本搜索的一个重要部分就是排序。
搜索结果中靠前的行等级值比靠后的行高。
查询扩展
使用查询扩展时,对数据和索引进行两次扫描:
- 首先,进行一个基本的全文本搜索,找出与搜索条件匹配的所有行
- 其次, MySQL检查这些匹配行并选择所有有用的词,MySQL再次进行全文本搜索,这次不仅使用原来的条件,而且还使用所有有用的词。
SELECT note_text
FROM productnotes
WHERE Match(note_text) Against('anvils' WITH QUERY EXPANSION);
布尔文本搜索
- 可以指定要排斥的词
- 可增加排列提示
- 但这种搜索耗时
SELECT note_text
FROM productnotes
WHERE Match(note_text) Against('heavy -rope*' IN BOOLEAN MODE);
上述语句中-rope*
明确地指出要排除包含rope*(任何以rope开始的词)的行。
Against('+safe +(<combination)' IN BOOLEAN MODE)
搜索匹配词safe和combination,降低后者等级Against('"rabbit bait"' IN BOOLEAN MODE)
搜索包含短语rabbit bait的句子Against('>rabbit <carrot' IN BOOLEAN MODE)
增加前者的等级,降低后者的等级- 需要注意的是,在布尔方式中,返回的行不排序
全文本搜索使用说明
- 如果一个词出现在50%以上的行中,则它作为一个非用词被忽略,50%规则不用于
IN BOOLEAN MODE
- 表中行数必须大于3行,否则不返回结果(因为每个字不能大于50%)
- 忽略词中单引号,don’t记为dont