Skip to Content

BCB5 使用 Regular Expression

過去為了工作需要,陸續在 BCB5 加進了支持 Unicode、資料庫的元件,當時還說未來最希望找到支援 Regular Expression (正規表達式,底下簡稱 RE) 的元件。前二天要把一個 perl 的程式移植到 BCB 來,因為該 perl 程式大量使用了 RE ,所以不得不停下工作,開始測試支援 RE 的資料。

這幾年的寫程式經驗中,perl 曾把我帶到另一個領域,最令人激賞的就是 perl 的 hash 及 RE,因為工作中有許多處理文字的問題,這些用 c++ 來寫非常不便,但 perl 的魔力卻讓這些事變的簡單許多,若不考慮圖形介面與效率的程式,perl 幾乎就是我隨手寫程式的工具了。

這幾月又重拾 BCB 寫程式,也開始用 set 及 map 來取代 perl 的 hash(BCB 6 內含的 STLport 已有 hash_set 及 hash_map,應該更好用,BCB5 還要自己去找來安裝),如今 BCB 找到了內嵌式的資料庫,若再加上 RE 的功能,那真是如虎添翼,寫起程式一定是更加得心應手了。

我找到幾個相關的資料,網址如下:

TRegExpr: http://www.regexpstudio.com (本站有些網址連結都會少了開頭的 www,若發現連結失敗,要自行加上 www)

PCRE: http://www.pcre.org

TPerlRegEx: http://www.regular-expressions.info/delphi.html

TropicSoft: http://www.tropicsoft.com/Components/RegularExpression/index.html

Regex++: http://ourworld.compuserve.com/homepages/John_Maddock/regexpp.htm

最初是找到的 TRegExpr 只有一個 pascal 檔,很容易使用,也很方便,但因為是 pascal 寫的,我擔心效率不夠好,就繼續研究其他的。

PCRE 好像是 c++ 寫的,效率應該很好,有一些元件都是使用它來包裝的。我後來有發現 BCB5 好像就有內含,不過用起來似乎很麻煩,我就暫時放棄學習。

TPerlRegEx 據說就是用 PCRE 包裝的,而且他名稱上有 perl,深得我心,不過使用上一直很不順,結果還會有問題,所以也暫時放棄。

TropicSoft 那一個我沒有試,因為它要安裝,所以我只是下載回來放著。

Regex++ 據說效率很好,使用 c++ 撰寫的,不過因為他是用 template 的方式設計,而我對 STL 研究不多,我比較習慣用 VCL 提供的元件。

花了不少時間研究後,最後還是先決定使用 TRegExpr,因為工作結案有時間壓力,沒法做太多研究。

TRegExpr 試起來效果不錯,基本功能都成功,底下就簡介幾個研究出來的功能。

■ 使用方法

把 RegExpr.pas 加入 project 中,先 compiler 它,讓它產生 RegExpr.hpp,並在要使用的程式中加入底下這一行:

#include "RegExpr.hpp"

■ 宣告

TRegExpr 可以宣告後使用,也可以利用一些隱含宣告的函式來執行,若要自行宣告物件,可用如下方法:

TRegExpr * regex = new TRegExpr;
....
delete regex;

■ 比對 Match

1.直接比對

if(ExecRegExpr("\\d", "My id is 1234.")) ShowMessage("match");

這類似 perl 的

$_ = "My id is 1234.";
if(/\d/) {print "match";}

注意:在 c++ 中,\ 符號要改用 \\,才不會出錯。

2.使用物件操作

regex->Expression = "(\\d+)";
regex->InputString = "abc123ijk456xyz";
if(regex->Exec())
{
do
{
ShowMessage(regex->Match[1]);
} while(regex->ExecNext());
}

類似 perl 這二行:

$_ = "abc123ijk456xyz";
while(/(\d+)/g) { print $1;}

簡單介紹幾個屬性與方法:

regex->InputString 輸入的原始字串
regex->ExecRegExpr 要比對的格式

regex->Exec() 在 InputString 比對 ExecRegExpr
regex->Exec("原始字串") 也可由參數傳入要比對的字串
regex->ExecNext() 進行下一筆比對

比對之後:

regex->SubExprMatchCount 大概是有幾個括號引用, 例如 "..(\d)..(\d).." 表示有二個括號
regex->Match[n] 每一個符合字串的內容
regex->MatchPos[n] 每一個符合字串的位置
regex->MatchLen[n] 每一個符合字串的長度
n 的數字類似 perl 的 $1 , $2, , 不過 0 則表示全部, 例如 ".(.)." , $0 表示全部的三個字, $1 是中間的字.

■ 分割 Split

1.直接處理

TStringList * slResult = new TStringList; // 存放結果用的
SplitRegExpr("\\s*,\\s*", "abc ,123 , xyz", (Classes::TStrings *) slResult);

類似 perl 這一行:

@result = split(/\s*,\s*/,"abc ,123 , xyz");

2.使用物件操作

TStringList * slResult = new TStringList; // 存放結果用的
regex->Expression = "\\s*,\\s*";
regex->Split("abc ,123 , xyz", (Classes::TStrings *) slResult);

■ 取代 Replace

1.直接處理

AnsiString sTmp = ReplaceRegExpr ("\\d(\\d)(\\d)", "phone 035 and 076 bye", "$2:$1", true);

傳回 sTmp = "phone 5:3 and 6:7 bye"

類似 perl 這二行:

$_ = "phone 035 and 076 bye";
s/\d(\d)(\d)/$2:$1/g;

若最後參數為 false , 表示 $1, $2 不代表正規式字串中的括號內容。

傳回 sTmp = "phone $2:$1 and $2:$1 bye"

注意:這裡的取代是全部取代,類似 perl 的 /g 參數。所以若要做單一取代,要自己在正規式中寫清楚。

2.使用物件操作

regex->Expression = "\\d(\\d)(\\d)";
AnsiString sTmp = regex->Replace("phone 035 and 076 bye", "$2:$1",true);

有了以上這些功能,BCB 要處理許多資料真的會方便很多,只是不知 TRegExpr 效率如何?若有機會,還是要試試 PCRE 的相關元件。

回應

回應瀏覽選項

選擇你喜歡的顯示回應的模式,並點選「儲存設定」,以啟用你所做的變更。

沒錯! 就是這個! 不過看來Regex是沒有比大小功能的

沒錯!
就是這個!

不過看來Regex是沒有比大小功能的
還是得再用c++來比較數值大小 ^ ^

謝謝版大囉!

比對字串後再比數字大小的功能

我大概會這樣做, 不知這是不是你想要的功能?

regex->Expression = "(\\d+).(\\d+)";
regex->InputString = "1-6";
if(regex->Exec())
{
int a = AnsiString(regex->Match[1])).ToInt();
int b = AnsiString(regex->Match[2])).ToInt();

if(a>b) ....;
else .....;
}

比方說像是 "1-6" 我想比較1、3碼的數字大小 不知道

比方說像是
"1-6"
我想比較1、3碼的數字大小
不知道這方面的功能Regex是否可以辦到呢?

比對字串後再比數字大小的功能

我不太懂 "比對字串後再比數字大小的功能" 的意思.

所以我大概沒用過這類功能, 不過我也想了解一下這是什麼意思?

版大您好,再請教一下,TRegExpr它有內建比對字串後再

版大您好,再請教一下,TRegExpr它有內建比對字串後再比數字大小的功能呢?

回應瀏覽選項

選擇你喜歡的顯示回應的模式,並點選「儲存設定」,以啟用你所做的變更。

發表新回應

這個欄位的內容會保密,不會公開顯示。
  • 自動將網址與電子郵件地址轉變為連結。
  • 自動斷行和分段。
  • 可使用的 HTML 標籤:<a> <address> <b> <blockquote> <br> <caption> <center> <cite> <code> <dd> <del> <div> <dl> <dt> <em> <h1> <h2> <h3> <h4> <h5> <h6> <hr> <i> <img> <ins> <li> <ol> <p> <pre> <span> <strike> <strong> <sub> <sup> <table> <tbody> <td> <th> <tr> <u> <ul>
    Allowed Style properties: background, background-attachment, background-color, background-image, background-position, background-repeat, border, border-bottom, border-bottom-color, border-bottom-style, border-bottom-width, border-collapse, border-color, border-left, border-left-color, border-left-style, border-left-width, border-right, border-right-color, border-right-style, border-right-width, border-spacing, border-style, border-top, border-top-color, border-top-style, border-top-width, border-width, bottom, caption-side, clip, color, direction, empty-cells, font, font-family, font-size, font-size-adjust, font-stretch, font-style, font-variant, font-weight, height, left, letter-spacing, line-height, list-style, list-style-image, list-style-position, list-style-type, margin, margin-bottom, margin-left, margin-right, margin-top, max-height, max-width, min-height, min-width, overflow, padding, padding-bottom, padding-left, padding-right, padding-top, right, table-layout, text-align, text-decoration, text-indent, text-transform, top, unicode-bidi, vertical-align, white-space, width, word-spacing, z-index

更多關於格式選項的資訊

CAPTCHA
驗證碼只有阿拉伯數字, 這是躲廣告用的, 麻煩你輸入了.
Image CAPTCHA
Enter the characters shown in the image.


story | about seo