匹配URL地址
匹配目多級(jí)子目錄以及可選的args
匹配目標(biāo)地址或者主機(jī)名以及可選的port
匹配協(xié)議名以及可選的username:password
雖然Java不支持嵌入條件未舟,但想要匹配美國(guó)郵政編碼的話可以使用\b\d{5}(-\d{4})?(?!-)\b
Java的RegEx不支持嵌入條件也不支持POSIX元字符類(lèi)
正則表達(dá)式 想匹配出需要的內(nèi)容很容易實(shí)現(xiàn),但是要求其不能匹配出我們不需要的內(nèi)容(即精確匹配)卻很困難
精確匹配郵箱地址
除了正前后查找還有舞骆,負(fù)前后查找琼富,他們的操作符分別是
(?!)
和 (?<!)
規(guī)則類(lèi)似
在Ea
和Eb
表達(dá)式蠕趁,前者匹配長(zhǎng)度可以是任意的
后者則必須是固定的掏呼,不能出現(xiàn)諸如*
+
{2,}
類(lèi)似的表達(dá)式
否則如果使用的是Java RegEx
的話贮匕,將拋出
Exception in thread "main" java.util.regex.PatternSyntaxException: Look-behind group does not have an obvious maximum length near index XX
但如果如果是集合或者單個(gè)字符往史,卻可以配合使用如
(?<=[a-z]*)
(?<=\d*)
(?<=\w+)
(?<=f*)
但這些是非法的
(?<=a\w*)
(?<=k\d*)
(?<=\w\w+)
(?<=aa+)
換句話說(shuō),如果(positive lookahead)
要匹配不固定長(zhǎng)黍瞧,那么只能是單個(gè)集合
(?<=[afgvds]{2,})
這也是一個(gè)合法的向后查找
(?=Ea)
為向前查找诸尽,在一個(gè)表達(dá)式的尾部
(?<=Eb)
為向后查找,在一個(gè)表達(dá)式的尾部
Java
即支持正向前查找(positive lookahead)
印颤,也支持正向后查找(positive lookbehind)
,他們是對(duì)某一位置的前后進(jìn)行查找您机,但它們并不是匹配結(jié)果的一部分。
Java RegEx
不支持\U
\u
\L
\l
\E
這樣的元字符
但是Intellj IDEA
支持
還原操作
RegEx | Replace |
---|---|
\((\d{3})\) (\d{3}-\d{4}) |
$1-$2 |
替換操作
RegEx | Replace |
---|---|
(\d{3})-(\d{3})(-)(\d{4}) |
($1) $2-$4 |
(\d{3})-(\d{3}-)(\d{4}) |
($1) $2$3 (而不是 ($1) $2-$3 必須要跨度大于1時(shí),- 才被轉(zhuǎn)義) |
(\d{3})-(\d{3}-\d{4}) |
($1) $2 |
(?<header>\d{3})-(?<tail>\d{3}-\d{4}) |
(${header}) ${tail} |
替換前 | 替換后 |
---|---|
494-939-5505 | (494) 939-5505 |
427-836-2491 | (427) 836-2491 |
142-620-0294 | (142) 620-0294 |
246-767-4276 | (246) 767-4276 |
585-328-1029 | (585) 328-1029 |
子表達(dá)式可用來(lái)進(jìn)行回溯引用匹配年局,用
\1,\2,...\n
來(lái)分別代表第n個(gè)表達(dá)式
但如果子表達(dá)式的相對(duì)位置發(fā)生了變化际看,整個(gè)模式也許就不能再完成原來(lái)的工作,刪除或添加子表達(dá)式的后果可能更為嚴(yán)重矢否。
所以仲闽,一些比較新的正則表達(dá)式實(shí)現(xiàn)還支持命名捕獲
:給某個(gè)子表達(dá)式起一個(gè)唯一的名字,然后用這個(gè)名字(而不是相對(duì)位置)來(lái)引用這個(gè)子表達(dá)式.
Java RegEx 支持命名捕獲僵朗,可混合使用編號(hào)和命名來(lái)引用前面子表達(dá)式的內(nèi)容
public static void main(String[] args) {
String input = "<BODY>\n" +
"<H1>Welcome to my Homepage</H1>\n" +
"Content is divided into two sections:<BR>\n" +
"<H2>ColdFusion</H2> <h2>ColdFusion</h2> <H3>Wireless</H5>\n" +
"Information about Macromedia ColdFusion.\n" +
"<H3>Wireless</H3>\n" +
"<H3>Wireless</h3>\n" +
"Information about Bluetooth, 802.11, and more.\n" +
"</BODY>";//<(?<x>[Hh])(?<y>[1-6]).*?\1\k<y>>
Pattern pattern = Pattern.compile("<(?<x>[Hh])(?<y>[1-6]).*?\\1\\k<y>>");
Matcher matcher = pattern.matcher(input);
System.out.println(pattern.pattern());
while (matcher.find()) {
System.out.println(matcher.group(0));//等價(jià)matcher.group()
System.out.println(matcher.group(1));//回溯引用第一個(gè)子表達(dá)式匹配到的內(nèi)容
System.out.println(matcher.group(2));//回溯引用第二個(gè)子表達(dá)式匹配到的內(nèi)容
System.out.println(matcher.group("x"));//采用命名捕獲赖欣,回溯引用第一個(gè)子表達(dá)式匹配到的內(nèi)容
System.out.println(matcher.group("y"));//采用命名捕獲屑彻,回溯引用第二個(gè)子表達(dá)式匹配到的內(nèi)容
}
System.out.println(matcher.toMatchResult().groupCount());//返回子表達(dá)式的個(gè)數(shù)
}
匹配1個(gè)字節(jié)能表達(dá)的范圍0-255,使用
正則表達(dá)式\b(2[0-4]\d|25[0-5]|1?\d{1,2})\b
而不是\b(1?\d{1,2}|2[0-4]\d|25[0-5])\b
假如使用(1?\d{1,2}|2[0-4]\d|25[0-5])
匹配255時(shí)候顶吮,將匹配25
和5
而使用(1?\d{1,2}|2[0-4]\d|25[0-5])\.
匹配255.時(shí)候社牲,將匹配255.
而不是55.
但要匹配55.
,則使用\B(1?\d{1,2}|2[0-4]\d|25[0-5])\.
如果使用了(?m)
的多行模式匹配悴了,那么^
將匹配\n
的結(jié)束位置膳沽,
$
將匹配\n
的開(kāi)始位置
Intellij IDEA
默認(rèn)使用多行模式匹配
Java RegEx
支持使用?(m)
進(jìn)行多行模式匹配
[\s\S]
將匹配任意字符類(lèi)似的都具有該功能如[\w\W]
,[\d\D]
(.|\n)
也可以真正的匹配任意字符
input = " a\n" +
" /** this is a test \n" +
"code \n" +
"wo fas ga hdh sha\n" +
"end?\n" +
"*/*/\n" +
"*/";//(?m)^\s*/\*[\S\s]*?\*/
Pattern pattern = Pattern.compile("(?m)^\\s*/\\*[\\S\\s]*?\\*/");
Matcher matcher = pattern.matcher(input);
while (matcher.find())
System.out.println("[" + matcher.start() + ",\n"
+ matcher.group()
+ "\n," + matcher.end() + "]");
輸出結(jié)果:
[3,
/** this is a test
code
wo fas ga hdh sha
end?
*/
,55]
^.*$可以匹配任意的非空字符串
\<
和\>
也用來(lái)匹配單詞邊界,前者匹配單詞開(kāi)頭让禀,后者匹配單詞結(jié)尾挑社,
但是Java
提供的正則表達(dá)式和Intellij IDEA
都不支持,egrep
程序支持
位置匹配元字符 | 功能描述 |
---|---|
\b | 不匹配任何字符,匹配\w與\W之間的位置 |
\B | 不匹配任何字符,匹配\w與\w或\W與\W之間的位置 |
匹配連線符
string | regex |
---|---|
nine-digit | \b-\b |
nine- digit | \b-\B |
nine - digit | \B-\B |
nine -digit | \B-\b |
\b
匹配且只匹配一個(gè)位置巡揍,不匹配任何字符痛阻。用\bcat\b
匹配到的字符串的長(zhǎng)度是3個(gè)字符(c,a,t)
,不是5個(gè)字符。
貪婪型元字符 | 懶惰型元字符 |
---|---|
* | *? |
+ | +? |
{m,} | {m,}? |
{m,n} | {m,n}? |
對(duì)于下面的那種情況腮敌,使用<[Bb]>.{1,16}</[Bb]>
也會(huì)導(dǎo)致過(guò)度匹配.
M{X(,Y)} ,Y
是可選的
且0=<X<=Y
表示前面的M模式
將出現(xiàn)至少X
次阱当,至多Y
次
?
是一個(gè)元字符,如果要匹配?本身糜工,就必須使用它的轉(zhuǎn)義序列\?
該元字符的功能是匹配0個(gè)或1個(gè)字符
\*
是一個(gè)元字符弊添,如果要匹配*本身,就必須使用它的轉(zhuǎn)義序列\\*
該元字符的功能是匹配0個(gè)或多個(gè)字符
[\r]?\n
用來(lái)兼容在window和linux/unix上的換行符兼容
+
是一個(gè)元字符油坝,如果要匹配+本身,就必須使用它的轉(zhuǎn)義序列\+
該元字符的功能是匹配一個(gè)或多個(gè)字符(或字符集合),但至少匹配一個(gè)
Java 和 Intellij IDEA 都不支持POSIX字符類(lèi)`
可以使用16進(jìn)制或者是8進(jìn)制來(lái)表達(dá)正則表達(dá)式刨裆,但是用這種方式表達(dá)出的字符都是普通字符澈圈,
如[\060\x2d\071]可以翻譯為[0-9]但是這個(gè)集合只包含0 - 9三個(gè)字符,等價(jià)于[0\-9]
正則表達(dá)式大小寫(xiě)敏感,而且通常對(duì)元字符來(lái)說(shuō)大寫(xiě)是小寫(xiě)的取非帆啃,如
\w \W 前者等價(jià) [a-zA-Z0-9_]瞬女,w是 word 的意思,類(lèi)似還有很多如
\d \D 前者等價(jià) [0-9]努潘,d是 digit 的意思
input = "1-8-5-189";//[0-5-9] 匹配不到8诽偷,正則表達(dá)式采用的貪心的方式0-5集合- 和9 組成的集合
Pattern pattern = Pattern.compile("[0-5-9]");
Matcher matcher = pattern.matcher(input);
var myArray = new Array();
...
if (myArray[0] == 0) {
...
}
if (myArray[1] == 0) {
...
}
if (myArray[2] == 0) {
...
}
if (myArray[3] == 0) {
...
}
matches here using regex:
if (myArray[[0-9]] == 0) {\n...\n}
任何的一個(gè)元字符如果想要匹配其本身,都可以通過(guò)加上一個(gè)反斜杠做為其前綴的辦法疯坤。
.和[類(lèi)原始就是元字符报慕, t和n類(lèi)必須轉(zhuǎn)義后才算是元字符
package regex;
import java.util.regex.MatchResult;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
* Created by E on 2017/8/1.
*/
@SuppressWarnings("UnusedAssignment")
public class _01 {
//以下測(cè)試的正則表達(dá)式都適用于java語(yǔ)言中的字符串表達(dá)的正則表達(dá)式
public static void main(String[] args) {
String input;
input = " car scar CAR Car CaR carry incarerate car carcar";//[Cc][Aa][Rr] 匹配所有car忽略大小寫(xiě)
input = "Hello, my name is Ben. Please visit my website at http://www.forta.com/.ben";//純文本匹配
String s = "sales1.xls " +
"orders3.xls" +
" sales2.xls" +
" sales3.xls" +
" apac1.xls" +
" europe2.xls" +
" na1.xls" +
" na2.xls" +
" sa1.xls ";//.a.\\. 對(duì)于后面的\\對(duì)應(yīng)一個(gè)java轉(zhuǎn)義為一個(gè)反斜杠,然后\.告訴正則表達(dá)式這不是一個(gè)模式贴膘,純文本
input = s;
input = "\\ 123.";//\\\\ java轉(zhuǎn)義為兩個(gè)\\卖子,正則表達(dá)式轉(zhuǎn)義成1個(gè)杠,然后匹配 字符串里面的一個(gè)杠杠\
input = "a\n";//a.無(wú)法匹配失敗 .匹配任意字符除\n刑峡,\轉(zhuǎn)義
input = "a\n";//a\\n \n匹配換行
input = s + " usal.xls";//[ns]a.\.xls 元字符使用
input = "The phrase \"regular expression\" is often\n" +
"abbreviated as RegEx or regex";//[Rr]eg[Ee]x
input = "sa2.java sa3.java sa6.java sa4.java sal.java ana3.java";//[ns]a[2-4].ja
input = "aaaaaaa";//aaa 只會(huì)匹配出2個(gè)洋闽,不會(huì)重疊匹配
input = "[a\\";//\\[a\\ , [Z-a]a[Z-a]
input = "<BODY BGCOLOR=\"#33A6b3\" TEXT=\"#FFfFFF\" MARGINWIDTH=\"0\" MARGINHEIGHT=\"0\" TOPMARGIN=\"0\" LEFTMARGIN=\"0\">";//#[0-9A-Fa-f][0-9A-Fa-f][0-9A-Fa-f][0-9A-Fa-f][0-9A-Fa-f][0-9A-Fa-f]
input = "a2 b3 n4 zu qe su nd n8 68 4a t6";//[a-z][^2-4 86] X-Y,X和Y僅指單個(gè)字符對(duì)于后面的字符X都將屬于這個(gè)集合
//[.]與\.等價(jià),不然如[.af]沒(méi)有意義af已經(jīng)被包括在.所描述的集合范圍內(nèi)了,所以將失去他的原本功能
Pattern pattern = Pattern.compile("");
Matcher matcher = pattern.matcher(input);
int count = 0;
while (matcher.find()) {//輸出
System.out.println("[" + matcher.start() + "," + matcher.group() + "," + matcher.end() + "]");
count++;
}
System.out.println(count);
}
}