視頻下載網站軟件做副屏網絡營銷的宏觀環(huán)境
通配符和正則表達式
本章介紹什么是通配符、如何使用通配符以及怎樣使用LIKE操作符進行通配搜索,以便對數(shù)據進行復雜過濾;如何使用正則表達式來更好地控制數(shù)據過濾。
目錄
- 通配符和正則表達式
- LIKE操作符
- 百分號(%)通配符
- 下劃線(_)通配符
- 通配符使用技巧
- 正則表達式
- MySQL常用正則
- 基本字符匹配
- OR匹配
- 匹配幾個字符之一
- 匹配范圍
- 匹配特殊字符
- 匹配字符類
- 匹配多個實例
- 定位符
LIKE操作符
在之前的案例中,我們都是用確定的條件進行查找和篩選,并沒有實現(xiàn)模糊查詢,比如要查找名字中有王這個字的數(shù)據。這種需求就需要使用通配符來解決。
通配符:(wildcard) 用來匹配值的一部分的特殊字符。
搜索模式:(search pattern)由字面值、通配符或兩者組合構成的搜索條件。
為在搜索子句中使用通配符,必須使用LIKE操作符。LIKE指示MySQL,后跟的搜索模式利用通配符匹配而不是直接相等匹配進行比較。
百分號(%)通配符
最常使用的通配符是百分號(%)。在搜索串中,%表示任何字符出現(xiàn)任意次數(shù)。
【示例】在employees表中查詢first_name以al開頭的條目信息
SELECT *
FROM `employees`
WHERE first_name LIKE 'al%';
運行結果:
通配符可在搜索模式中任意位置使用,并且可以使用多個通配符。
【示例】在employees表中查詢first_name中包含la的信息
SELECT first_name
FROM `employees`
WHERE first_name LIKE '%la%';
運行結果:
尾空格可能會干擾通配符匹配。例如,在保存詞anvil 時, 如果它后面有一個或多個空格, 則子句WHERE
prod_name LIKE '%anvil’將不會匹配它們,因為在最后的l后有多余的字符。解決這個問題的一個簡單的辦法是在搜索模式最后附加一個%。一個更好的辦法是使用函數(shù)(后續(xù)文章會詳細介紹函數(shù)用法)去掉首尾空格。
雖然似乎%通配符可以匹配任何東西,但有一個例外,即NULL。即使是WHERE first_name LIKE '%'也不能匹配用值NULL作為名字的行。
下劃線(_)通配符
另一個常用的通配符是下劃線(_)。下劃線的用途與%一樣,但下劃線只匹配單個字符而不是多個字符。
【示例】查詢employees表中first_name中以l開頭一共四個字符的信息條目
SELECT first_name
FROM `employees`
WHERE first_name LIKE 'l___';
運行結果:
與%能匹配0個字符不一樣,_總是匹配一個字符,不能多也不能少。
通配符使用技巧
正如所見,MySQL的通配符很有用。但這種功能是有代價的:通配符搜索的處理一般要比前面討論的其他搜索所花時間更長。這里給出一些使用通配符要記住的技巧。
- 不要過度使用通配符。如果其他操作符能達到相同的目的,應該使用其他操作符。
- 在確實需要使用通配符時,除非絕對有必要,否則不要把它們用在搜索模式的開始處。把通配符置于搜索模式的開始處,搜索起來是最慢的。
- 仔細注意通配符的位置。如果放錯地方,可能不會返回想要的數(shù)據??傊?#xff0c;通配符是一種極重要和有用的搜索工具,以后我們經常會用到它。
正則表達式
對于基本的過濾(或者甚至是某些不那么基本的過濾),前面介紹的過濾方法+通配符就足夠了。但隨著過濾條件的復雜性的增加,WHERE子句本身的復雜性也有必要增加。
這也就是正則表達式變得有用的地方。正則表達式是用來匹配文本的特殊的串(字符集合)。如果你想從一個文本文件中提取電話號碼,可以使用正則表達式。如果你需要查找名字中間有數(shù)字的所有文件,可以使用一個正則表達式。如果你想在一個文本塊中找到所有重復的單詞,可以使用一個正則表達式。如果你想替換一個頁面中的所有URL為這些URL的實際HTML鏈接,也可以使用正則表達式實現(xiàn)。
所有種類的程序設計語言、文本編輯器、操作系統(tǒng)等都支持正則表達式。有見識的程序員和網絡管理員已經關注作為他們技術工具重要內容的正則表達式很長時間了。
正則表達式用正則表達式語言來建立,正則表達式語言是用來完成剛討論的所有工作以及更多工作的一種特殊語言。此處我也僅僅是為你介紹一些簡單和常用的正則語言,更詳細的內容可以關注我的博客,我后續(xù)會專門為正則語言開一個專欄。
MySQL常用正則
MySQL用WHERE子句對正則表達式提供了初步的支持,允許你指定正則表達式過濾SELECT檢索出的數(shù)據。
基本字符匹配
我們從一個非常簡單的例子開始。
【示例】下面的語句檢索employees表中列first_name包含文本al的所有行:
SELECT first_name
FROM `employees`
WHERE first_name REGEXP 'al';
運行結果:
除關鍵字LIKE被REGEXP替代外,這條語句看上去非常像使用LIKE的語句。它告訴MySQL,REGEXP后所跟的東西作為正則表達式處理。
REGEXP
是一個用于執(zhí)行正則表達式匹配的函數(shù),它允許你在SQL查詢中進行復雜的文本模式匹配?;菊Z法如下:
expr REGEXP pattern
這里:
expr
是你想要檢查是否匹配正則表達式模式的表達式(通常是字段名或字符串值)。pattern
是定義匹配規(guī)則的正則表達式模式。
LIKE匹配整個列。如果被匹配的文本在列值中出現(xiàn),LIKE將不會找到它,相應的行也不被返回(除非使用
通配符)。而REGEXP在列值內進行匹配,如果被匹配的文本在列值中出現(xiàn),REGEXP將會找到它,相應的行將被返回。這是一個非常重要的差別。
OR匹配
為搜索兩個串之一(或者為這個串,或者為另一個串),使用|
【示例】檢索employees表中列first_name包含文本al或ch的所有行:
SELECT first_name
FROM `employees`
WHERE first_name REGEXP 'al|ch';
運行結果:
匹配幾個字符之一
如果你只想匹配特定的字符,可通過指定一組用[和]括起來的字符來完成,如下所示:
【示例】檢索employees表中列first_name包含文本al、bl、cl的所有行:
SELECT first_name
FROM `employees`
WHERE first_name REGEXP '[abc]l';
運行結果:
這里,使用了正則表達式[abc]l。[abc]定義一組字符,它的意思是匹配a或b或c,因此,al和cl都匹配且返回(沒有bl)。
正如所見,[]是另一種形式的OR語句。事實上,正則表達式[abc]l為[a|b|c]l的縮寫,也可以使用后者。
匹配范圍
集合可用來定義要匹配的一個或多個字符。例如,下面的集合將匹配數(shù)字0到9:
[0-9]
范圍不一定只是數(shù)值的,[a-z]匹配任意字母字符。
匹配特殊字符
正則表達式語言由具有特定含義的特殊字符構成。我們已經看到.、[]、|和-等,還有其他一些字符。如果你需要匹配這些字符,應該使用轉義為了匹配特殊字符,必須用\為前導。\\-
表示查找-,\\.
表示查找.
。
為了匹配反斜杠(\)字符本身,需要使用\\\
。
匹配字符類
存在找出你自己經常使用的數(shù)字、所有字母字符或所有數(shù)字字母字符等的匹配。為更方便工作,可以使用預定義的字符集,稱為字符類(character class)。下表列出字符類以及它們的含義。
類 | 說明 |
---|---|
[:alnum:] | 任意字母和數(shù)字(同[a-zA-Z0-9]) |
[:alpha:] | 任意字符(同[a-zA-Z]) |
[:blank:] | 空格和制表(同[\t]) |
[:cntrl:] | ASCII控制字符(ASCII 0到31和127) |
[:digit:] | 任意數(shù)字(同[0-9]) |
[:graph:] | 與[:print:]相同,但不包括空格 |
[:lower:] | 任意小寫字母(同[a-z]) |
[:print:] | 任意可打印字符 |
[:space:] | 包括空格在內的任意空白字符(同[\f\n\r\t\v]) |
[:upper:] | 任意大寫字母(同[A-Z]) |
[:punct:] | 既不在[:alnum:]又不在[:cntrl:]中的任意字符 |
[:xdigit:] | 任意十六進制數(shù)字(同[a-fA-F0-9]) |
匹配多個實例
目前為止使用的所有正則表達式都試圖匹配單次出現(xiàn)。如果存在一個匹配,該行被檢索出來,如果不存在,檢索不出任何行。但有時需要對匹配的數(shù)目進行更強的控制。例如,你可能需要尋找所有的數(shù),不管數(shù)中包含多少數(shù)字,或者你可能想尋找一個單詞并且還能夠適應一個尾隨的s(如果存在),等等。
重復元字符
元字符 | 說明 |
---|---|
* | 0個或多個匹配 |
+ | 1個或多個匹配(等于{1,}) |
? | 0個或1個匹配(等于{0,1}) |
{n} | 指定數(shù)目的匹配 |
{n,} | 不少于指定數(shù)目的匹配 |
{n,m} | 匹配數(shù)目的范圍(m不超過255) |
【示例】
\\([0-9] sticks?\\)
\\
(匹配),[0-9]匹配任意數(shù)字,sticks?匹配stick和sticks(s后的?使s可選,因為?匹配它前面的任何字符的0次或1次出現(xiàn)),``\`)匹配)。
【示例】匹配連在一起的任意4位數(shù)字。
[[:digit:]]{4}
定位符
為了匹配特定位置的文本,需要使用下表列出的定位符。
元字符 | 說明 |
---|---|
^ | 文本開始 |
$ | 文本結尾 |
[[:<:]] | 詞的開始 |
[[:>:]] | 詞的末尾 |
【示例】想找出以一個數(shù)(包括以小數(shù)點開始的數(shù))開始的所有產品
^[0-9\\.]
^的雙重用途: ^有兩種用法。在集合中(用[和]定義),用它來否定該集合,否則,用來指串的開始處。