細說正規表示式之斷言

2021-07-31 16:09:34 字數 1707 閱讀 1119

應該沒什麼問題吧。大概就是如果從頭匹配,則keyword前需要匹配不含,.的任意字元;如果不是從頭匹配的則keyword前必須有乙個,或者.且keyword和該符號之間不能再包含,.。後半部分的意思是一樣的就不多說了。

(注:\.為c#中匹配半形句號的寫法;*?為非貪婪匹配)

話說這道題貌似就到此為止了,那跟斷言有什麼關係呢?各位可以試一下,用這個方法匹配的結果前後基本都會帶上逗號句號,也就是說雖然我們只要關鍵句,但是正規表示式把符號也匹配進來了。或許有人說替換一下就好啦,但是在這裡我要強力推薦使用斷言。理由有二,先說第一點:斷言更優雅簡潔,逼格更高^_^

好啦,先讓我們先來看看斷言在這道題的寫法吧。

(^[^,\.]*|(?<=,|\.)[^,\.]*?)keyword.*?(?=(,|\.)|$)

吼了,看看和上面的有什麼不同吧。總共只有兩部分:(?<=,|\.)以及(?=(,|\.),很像似不似。那為什麼這兩句話能達到我們想要的效果呢,先岔開話題說一下斷言的分類:

(?=pattern)  零寬正向先行斷言(zero-width positive lookahead assertion) 

(?!pattern) 零寬負向先行斷言(zero-width negative lookahead assertion)

(?<=pattern) 零寬正向後行斷言(zero-width positive lookbehind assertion)

(?zero-width negative lookbehind assertion)

解釋一下:

(?=pattern)  要求當前位置開始向後的字串能匹配pattern。比如hello(?=world)匹配helloworld能夠成功

(?!pattern) 要求當前位置開始向後的字串不能匹配pattern。比如hello(?!world)匹配helloworld則失敗

(?<=pattern) 要求當前位置開始向前的字串能匹配pattern。比如(?<=hello)world匹配helloworld能夠成功

(?pattern) 要求當前位置開始向前的字串不能匹配pattern。比如(?hello)world匹配helloworld則失敗

而除了對於前後字串的限定之外,有沒有注意到他們都是零寬的,換句話說斷言只是條件,本身並不佔位匹配。那麼回頭看看上面的小題。

我將前後部分的(,|\.)分別用(?<=,|\.)以及(?=(,|\.)進行替代。相當於把原本的匹配行為換成了條件判斷行為: 前後包含逗號或句號則結果為true。這樣一來,最終匹配結果就不會包含前後的符號了^o^ 。

例如判斷一句話中包含this,但不包含that。

包含this比較好辦,一句話中不包含that,可以認為這句話中每個字元的前面都不是that或每個字元的後面都不是that。正規表示式如下:

^((?那麼上面最後的幾個正規表示式為什麼能夠成功呢,或者有人說這麼複雜怎麼記啊。其實很簡單,上面四個表示式都是乙個原理。先看看為什麼^((?

。 ok,斷言的講解到此為止~鞠躬~~

正規表示式之斷言

零寬斷言的意思是 匹配寬度為零,滿足一定的條件 斷言 我也不知道這個詞語是那個王八蛋發明的,簡直是太拗口了。零寬斷言用於查詢在某些內容 但並不包括這些內容 之前或之後的東西,也就是說它們像 b,那樣用於指定乙個位置,這個位置應該滿足一定的條件 即斷言 因此它們也被稱為零寬斷言。斷言用來宣告乙個應該為...

正規表示式之斷言

exp 零寬度正先行斷言 零寬度正先行斷言為例 先行 表示待校驗的位置在前,即校驗的位置在exp匹配的內容之前 d 表示校驗的位置後面是三個數字 d 表示校驗的位置後接著的是數字 表示校驗的位置後字串長度為5,因為加了字串開頭和結尾的元符號,所以這個表示式作用其實就是匹配長度為5的字串。由上面例子可...

正規表示式 斷言

密碼的正規表示式,要求是密碼8 16位,必須包含數字大小寫字母以及特殊字元 高人寫的 pwd pattern a z a z a za z0 9 經過學習,分析如下 a z 斷言,只匹配乙個位置 比如,你想匹配乙個 人 字,但是你只想匹配中國人的人字,不想匹配法國人的人,就可以用 中國 人 a z ...