|
地板

樓主 |
發(fā)表于 2009-6-30 09:32:22
|
只看該作者
如果對(duì)正則表達(dá)式的機(jī)理有一定了解,就可以借助這個(gè)經(jīng)驗(yàn)猜到這個(gè)函數(shù)大概是把正則表達(dá)
式字符串轉(zhuǎn)換成狀態(tài)機(jī)以便高效地匹配目標(biāo)字符串。如果以前用過其它編程語言的正則表達(dá)
式庫(kù)函數(shù),也可以借助這些經(jīng)驗(yàn)知道正則表達(dá)式在使用之前大多有一個(gè)預(yù)處理的步驟。另
外,對(duì)英文縮寫要有一定敏感性,函數(shù)名是regcomp,reg就是正則表達(dá)式,comp是compare還
是compile?如果是compare,那應(yīng)該有兩個(gè)相同類型的參數(shù)來做比較,就像strcmp,這里顯
然是compile,編譯,把字符串形式轉(zhuǎn)為二進(jìn)制形式,從另一個(gè)側(cè)面也驗(yàn)證了前面的猜測(cè)。這
些都是靠經(jīng)驗(yàn)而不是推理得到的,經(jīng)驗(yàn)有助于更快更準(zhǔn)確地理解,但不是必須的,因?yàn)槭聦?shí)
上我們通過上面基于傳入傳出參數(shù)的推理已經(jīng)猜出正確結(jié)論了,只不過有經(jīng)驗(yàn)的人會(huì)對(duì)自己
的猜測(cè)更自信。
對(duì)英文縮寫敏感是看man page和看代碼需要具備的最基本的能力,但這需要長(zhǎng)期的練習(xí)才能
找到感覺。也許你要學(xué)會(huì)一個(gè)函數(shù)怎么用并不必知道函數(shù)名和各個(gè)參數(shù)名是什么的縮寫,你
通過以上列舉的兩本爛書就可以學(xué)會(huì)怎么用,但如果總是回避man page,總是不去做猜縮寫
的練習(xí),就不可能看懂別人的代碼,不看別人的代碼就自己亂寫代碼,連變量名該怎么起都
不知道,寫出來的永遠(yuǎn)是垃圾代碼。對(duì)于regcomp這個(gè)函數(shù)名以及各參數(shù)名,regex是
regular expression,regcomp是regular expression compile。那么preg是什么?reg是
regular expression,p表示什么呢?表示指針?那是微軟的infamous的hungarian
notation,Linux上肯定不是這么用的,這里的p我猜是precompiled。cflags的c是什么?不
知道,但是跟下面一個(gè)函數(shù)對(duì)比來看:
C代碼
1. int regexec(const regex_t *preg, const char *string, size_t nmatch,
2. regmatch_t pmatch[], int eflags);
int regexec(const regex_t *preg, const char *string, size_t nmatch,
regmatch_t pmatch[], int eflags);
這個(gè)函數(shù)有個(gè)參數(shù)叫eflags。所以c是regcomp的c,而e是regexec的e,一個(gè)是編譯時(shí)的
flags,一個(gè)是執(zhí)行時(shí)的flags,這兩種flags的取值必然不同,下文必然會(huì)分別說明。這又是
一種猜測(cè):猜測(cè)下文的行文邏輯。這種猜測(cè)同樣是非常有助于理解的。后面幾個(gè)函數(shù)的函數(shù)
名和參數(shù)名是怎么縮寫的,留給讀者自己練習(xí)。
preg參數(shù)在regcomp中是傳出參數(shù),在regexec中卻是傳入?yún)?shù),根據(jù)推理,preg是由
regcomp函數(shù)填寫好之后傳給regexec函數(shù)用的,也就是說正則表達(dá)式以轉(zhuǎn)換之后的二進(jìn)制格
式傳給regexec函數(shù)來用。regexec又有一個(gè)字符串傳入?yún)?shù)string,還有兩個(gè)match參數(shù)表示
匹配結(jié)果,pmatch是傳出參數(shù),表示緩沖區(qū)首地址,nmatch表示緩沖區(qū)長(zhǎng)度(根據(jù)經(jīng)驗(yàn),這
類似于strncpy),這必然就是我一開始想要的my_expect_func了:
C代碼
1. int my_expect_func(傳入:正則表達(dá)式, 傳入:目標(biāo)字符串, 傳出:匹配結(jié)果);
2. 返回:錯(cuò)誤碼
int my_expect_func(傳入:正則表達(dá)式, 傳入:目標(biāo)字符串, 傳出:匹配結(jié)果);
返回:錯(cuò)誤碼
preg對(duì)應(yīng)正則表達(dá)式,pmatch和nmatch對(duì)應(yīng)匹配結(jié)果,因此string這個(gè)傳入?yún)?shù)必然是目標(biāo)
字符串了。pmatch是一個(gè)指針變量,但是寫成pmatch[],說明它指向的是一組而不是一個(gè)
regmatch_t類型的對(duì)象,這一組有多少個(gè)呢?用nmatch參數(shù)表示。和strncpy類似,這一組
regmatch_t對(duì)象應(yīng)該由我們事先分配好再傳給函數(shù)。因此這兩個(gè)函數(shù)應(yīng)該是這樣調(diào)用的:
C代碼
1. regex_t regobj;
2. regcomp(®obj, "正則表達(dá)式", 標(biāo)志位1|標(biāo)志位2|...);
3. regmatch_t matchbuf[10];
4. regexec(®obj, "目標(biāo)字符串", 10, matchbuf, 標(biāo)志位1|標(biāo)志位2|...);
regex_t regobj;
regcomp(®obj, "正則表達(dá)式", 標(biāo)志位1|標(biāo)志位2|...);
regmatch_t matchbuf[10];
regexec(®obj, "目標(biāo)字符串", 10, matchbuf, 標(biāo)志位1|標(biāo)志位2|...);
regmatch_t對(duì)象如何表示一個(gè)匹配呢?如果一個(gè)正則表達(dá)式模式在一個(gè)目標(biāo)字符串中有五次
出現(xiàn),如何表示這五次出現(xiàn)呢?可以猜測(cè)這個(gè)regmatch_t結(jié)構(gòu)體一定包含了在目標(biāo)字符串中
的匹配位置信息。另外,我傳進(jìn)去10個(gè)regmatch_t對(duì)象,如果只有五次匹配,函數(shù)返回后我
怎么知道前面五個(gè)對(duì)象是有效的匹配信息而后面是無效的呢?是不是通過一個(gè)參數(shù)或返回值
表示匹配次數(shù)的?該函數(shù)并沒有額外的參數(shù),而且快速翻看一下man page的RETURN
VALUE節(jié),這個(gè)函數(shù)返回值是錯(cuò)誤碼,也不表示匹配次數(shù)。那這個(gè)函數(shù)一定會(huì)在后面無效的
regmatch_t對(duì)象里填充一個(gè)特殊值,這就是推理,這個(gè)猜測(cè)將會(huì)在閱讀后面的文字時(shí)證實(shí)或
證偽,不管猜得對(duì)不對(duì),一定會(huì)在后面得到答案。 |
|