Tiếng AnhTiếng PhápTiếng Tây Ban Nha

Biểu tượng yêu thích OnWorks

perlfaq6 - Trực tuyến trên đám mây

Chạy perlfaq6 trong nhà cung cấp dịch vụ lưu trữ miễn phí OnWorks trên Ubuntu Online, Fedora Online, trình giả lập trực tuyến Windows hoặc trình mô phỏng trực tuyến MAC OS

Đây là lệnh perlfaq6 có thể được chạy trong nhà cung cấp dịch vụ lưu trữ miễn phí OnWorks bằng cách sử dụng một trong nhiều máy trạm trực tuyến miễn phí của chúng tôi như Ubuntu Online, Fedora Online, trình giả lập trực tuyến Windows hoặc trình mô phỏng trực tuyến MAC OS

CHƯƠNG TRÌNH:

TÊN


perlfaq6 - Biểu thức chính quy

PHIÊN BẢN


phiên bản 5.021009

MÔ TẢ


Phần này hơi nhỏ một cách đáng ngạc nhiên vì phần còn lại của Câu hỏi thường gặp có rất nhiều câu trả lời
liên quan đến các biểu thức chính quy. Ví dụ: giải mã một URL và kiểm tra xem có điều gì
là một số có thể được xử lý bằng biểu thức chính quy, nhưng những câu trả lời đó được tìm thấy ở những nơi khác
trong tài liệu này (trong perlfaq9: "Làm cách nào để giải mã hoặc tạo% -encodings đó trên web"
và perlfaq4: "Làm cách nào để xác định xem một đại lượng vô hướng có phải là một số / nguyên / số nguyên / float", là
tóm lược).

Làm thế nào có thể I mong đến sử dụng đều đặn biểu thức không có tạo không thể đọc được không thể giải thích được mã số?
Ba kỹ thuật có thể làm cho các biểu thức chính quy dễ bảo trì và dễ hiểu.

Nhận xét bên ngoài Regex
Mô tả những gì bạn đang làm và cách bạn đang thực hiện nó, sử dụng nhận xét Perl bình thường.

# chuyển dòng thành từ đầu tiên, dấu hai chấm và
# số ký tự trên phần còn lại của dòng
s / ^ (\ w +) (. *) / lc ($ 1). ":". chiều dài ($ 2) / meg;

Nhận xét bên trong Regex
Công cụ sửa đổi "/ x" làm cho khoảng trắng bị bỏ qua trong mẫu regex (ngoại trừ trong
lớp nhân vật và một số nơi khác), và cũng cho phép bạn sử dụng các nhận xét bình thường
ở đó, quá. Như bạn có thể tưởng tượng, khoảng trắng và nhận xét giúp ích rất nhiều.

"/ x" cho phép bạn biến điều này:

s {<(?: [^> '"] * |". *? "|'. *? ') +>} {} gs;

vào cái này:

s {<# dấu ngoặc nhọn góc mở
(?: # Dấu ngoặc kép phân nhóm không backreffing
[^> '"] * # 0 trở lên không phải> cũng không phải' cũng không phải"
| # hoặc cái gì đó khác
". *?" # một phần giữa dấu ngoặc kép (kết hợp keo kiệt)
| # hoặc cái gì đó khác
'. *?' # một phần giữa các dấu ngoặc kép (kết hợp keo kiệt)
) + # tất cả xảy ra một hoặc nhiều lần
> # dấu ngoặc nhọn đóng
} {} gsx; # thay thế bằng không, tức là xóa

Nó vẫn chưa hoàn toàn rõ ràng như văn xuôi, nhưng nó rất hữu ích để mô tả
ý nghĩa của từng phần của hoa văn.

Dấu phân cách khác nhau
Mặc dù chúng ta thường nghĩ về các mẫu được phân tách bằng các ký tự "/", chúng có thể
được phân định bằng hầu hết mọi ký tự. perlre mô tả điều này. Ví dụ: "s ///"
ở trên sử dụng dấu ngoặc nhọn làm dấu phân cách. Việc chọn một dấu phân cách khác có thể tránh việc trích dẫn
dấu phân cách trong mẫu:

NS/\/ usr\/địa phương/\/ usr\ / share / g; # lựa chọn dấu phân cách không hợp lệ
s#/ usr / local#/ usr / chia sẻ#NS; # tốt hơn

Sử dụng các dấu phân cách được ghép nối hợp lý thậm chí có thể dễ đọc hơn:

s{/ usr / local /}{/ usr / chia sẻ}NS; # vẫn tốt hơn

Tôi là rắc rối phù hợp kết thúc chi tiết hơn một hàng. Có gì Sai lầm?
Bạn không có nhiều hơn một dòng trong chuỗi mà bạn đang xem (có thể là), hoặc
nếu không, bạn không sử dụng (các) công cụ sửa đổi chính xác trên mẫu của mình (có thể).

Có nhiều cách để lấy dữ liệu nhiều dòng thành một chuỗi. Nếu bạn muốn nó xảy ra
tự động trong khi đọc đầu vào, bạn sẽ muốn đặt $ / (có thể là '' cho các đoạn văn hoặc
"undef" cho toàn bộ tệp) để cho phép bạn đọc nhiều dòng cùng một lúc.

Đọc perlre để giúp bạn quyết định cái nào trong số "/ s" và "/ m" (hoặc cả hai) bạn có thể muốn sử dụng:
"/ s" cho phép dấu chấm bao gồm dòng mới và "/ m" cho phép dấu mũ và đô la khớp với
dòng mới, không chỉ ở cuối chuỗi. Bạn cần đảm bảo rằng bạn đã thực sự
có một chuỗi nhiều dòng trong đó.

Ví dụ: chương trình này phát hiện các từ trùng lặp, ngay cả khi chúng kéo dài ngắt dòng (nhưng
không phải đoạn văn). Đối với ví dụ này, chúng tôi không cần "/ s" vì chúng tôi không sử dụng dấu chấm trong
biểu thức chính quy mà chúng tôi muốn vượt qua ranh giới dòng. Chúng ta cũng không cần "/ m" bởi vì
chúng tôi không muốn dấu mũ hoặc đô la khớp tại bất kỳ điểm nào bên trong bản ghi bên cạnh các dòng mới.
Nhưng bắt buộc phải đặt $ / thành thứ gì đó khác với giá trị mặc định, nếu không, chúng tôi sẽ không
thực sự đã bao giờ có một bản ghi nhiều dòng được đọc trong.

$ / = ''; # đọc toàn bộ đoạn văn, không chỉ một dòng
trong khi (<>) {
while (/ \ b ([\ w '-] +) (\ s + \ g1) + \ b / gi) {# từ bắt đầu alpha
print "Nhân bản $ 1 tại đoạn $. \ n";
}
}

Dưới đây là một số mã tìm các câu bắt đầu bằng "Từ" (sẽ bị hiểu bởi
nhiều người gửi thư):

$ / = ''; # đọc toàn bộ đoạn văn, không chỉ một dòng
trong khi (<>) {
while (/ ^ From / gm) {# / m làm cho ^ khớp với \ n
print "đứng đầu trong đoạn $. \ n";
}
}

Đây là mã tìm thấy mọi thứ giữa START và END trong một đoạn văn:

undef $ /; # đọc trong toàn bộ tệp, không chỉ một dòng hoặc đoạn văn
trong khi (<>) {
while (/START(.*?)END/sgm) {# / s thực hiện. ranh giới đường chéo
in "$ 1 \ n";
}
}

Làm thế nào có thể I kéo ra dòng giữa hai mô hình việc này đang tự on khác nhau dòng?
Bạn có thể sử dụng toán tử ".." hơi kỳ lạ của Perl (tài liệu trong perlop):

perl -ne 'print if / START / .. / END /' file1 file2 ...

Nếu bạn muốn văn bản chứ không phải dòng, bạn sẽ sử dụng

perl -0777 -ne 'print "$ 1 \ n" trong khi /START(.*?)END/gs' file1 file2 ...

Nhưng nếu bạn muốn các lần xuất hiện lồng nhau từ "START" đến "END", bạn sẽ phải đối mặt với
vấn đề được mô tả trong câu hỏi trong phần này về kết hợp văn bản cân bằng.

Đây là một ví dụ khác về việc sử dụng "..":

trong khi (<>) {
của tôi $ in_header = 1 .. / ^ $ /;
$ in_body của tôi = / ^ $ / .. eof;
# bây giờ hãy chọn giữa chúng
} tiếp tục {
$. = 0 nếu eof; # sửa $.
}

Làm thế nào do I phù hợp với XML, HTML, or khác khó chịu, xấu xí điều với a biểu thức chính quy?
Không sử dụng regexes. Sử dụng một mô-đun và quên đi các biểu thức chính quy. Các
Các mô-đun XML :: LibXML, HTML :: TokeParser và HTML :: TreeBuilder là những khởi đầu tốt, mặc dù mỗi
không gian tên có các mô-đun phân tích cú pháp khác chuyên biệt cho các tác vụ nhất định và các cách khác nhau
làm việc đó. Bắt đầu tại Tìm kiếm CPAN (http://metacpan.org/>) và tự hỏi ở tất cả các công việc
mọi người đã làm cho bạn rồi! :)

I đặt a đều đặn biểu hiện trong $/ nhưng it không làm việc. Có gì Sai lầm?
$ / phải là một chuỗi. Bạn có thể sử dụng những ví dụ này nếu bạn thực sự cần làm điều này.

Nếu bạn có File :: Stream, điều này thật dễ dàng.

sử dụng File :: Stream;

my $ stream = File :: Stream-> new (
$ filehandle,
dấu phân tách => qr / \ s *, \ s * /,
);

print "$ _ \ n" while <$ stream>;

Nếu bạn không có File :: Stream, bạn phải thực hiện thêm một chút công việc.

Bạn có thể sử dụng biểu mẫu sysread bốn đối số để liên tục thêm vào bộ đệm. Sau bạn
thêm vào bộ đệm, bạn kiểm tra xem bạn có dòng hoàn chỉnh hay không (sử dụng biểu thức chính quy của bạn).

địa phương $ _ = "";
while (sysread FH, $ _, 8192, length) {
while (s / ^ ((? s). *?) your_pattern //) {
bản ghi $ của tôi = $ 1;
# làm những thứ ở đây.
}
}

Bạn có thể làm điều tương tự với foreach và match bằng cách sử dụng cờ c và neo \ G, nếu
bạn không ngại toàn bộ tệp của bạn ở trong bộ nhớ ở cuối.

địa phương $ _ = "";
while (sysread FH, $ _, 8192, length) {
bỏ qua bản ghi $ của tôi (m / \ G ((? s). *?) your_pattern / gc) {
# làm những thứ ở đây.
}
substr ($ _, 0, pos) = "" nếu pos;
}

Làm thế nào do I Thay thế không phân biệt chữ hoa chữ thường on các LHS trong khi bảo quản trường hợp on các RHS?
Đây là một giải pháp Perlish đáng yêu của Larry Rosler. Nó khai thác các thuộc tính của bitwise xor trên
Chuỗi ASCII.

$ _ = "đây là trường hợp TEsT";

$ old = 'test';
$ new = 'thành công';

s {(\ Q $ old \ E)}
{uc $ mới | (uc $ 1 ^ $ 1).
(uc (substr $ 1, -1) ^ substr $ 1, -1) x
(chiều dài ($ mới) - chiều dài $ 1)
} egi;

in;

Và đây nó là một chương trình con, được mô phỏng theo phần trên:

bảo tồn phụ {
của tôi ($ cũ, $ mới) = @_;
my $ mask = uc $ old ^ $ old;

uc $ mới | $ mặt nạ.
substr ($ mask, -1) x (length ($ new) - length ($ old))
}

$ string = "đây là trường hợp TEsT";
$ string = ~ s / (test) / inherit_case ($ 1, "thành công") / egi;
in "$ string \ n";

Bản in này:

đây là một trường hợp SUcCESS

Thay vào đó, hãy giữ nguyên trường hợp của từ thay thế nếu nó dài hơn
ban đầu, bạn có thể sử dụng mã này, bởi Jeff Pinyan:

bảo tồn phụ {
của tôi ($ từ, $ đến) = @_;
my ($ lf, $ lt) = độ dài bản đồ, @_;

if ($ lt <$ lf) {$ from = substr $ from, 0, $ lt}
khác {$ từ. = substr $ đến, $ lf}

trả lại uc $ cho | ($ từ ^ uc $ từ);
}

Điều này thay đổi câu thành "đây là trường hợp SUcCess."

Chỉ để cho thấy rằng các lập trình viên C có thể viết C bằng bất kỳ ngôn ngữ lập trình nào, nếu bạn thích
giải pháp giống C hơn, tập lệnh sau làm cho sự thay thế có cùng trường hợp,
từng chữ cái, như bản gốc. (Nó cũng xảy ra chạy chậm hơn khoảng 240% so với
Giải pháp Perlish chạy.) Nếu thay thế có nhiều ký tự hơn chuỗi
được thay thế, trường hợp của ký tự cuối cùng được sử dụng cho phần còn lại của sự thay thế.

# Bản gốc của Nathan Torkington, được massage bởi Jeffrey Friedl
#
bảo quản phụ
{
của tôi ($ cũ, $ mới) = @_;
my $ bang = 0; # 0 = không thay đổi; 1 = lc; 2 = uc
my ($ i, $ oldlen, $ newlen, $ c) = (0, length ($ old), length ($ new));
my $ len = $ oldlen <$ newlen? $ oldlen: $ newlen;

for ($ i = 0; $ i <$ len; $ i ++) {
if ($ c = substr ($ old, $ i, 1), $ c = ~ / [\ W \ d _] /) {
$ bang = 0;
} elsif (lc $ c eq $ c) {
substr ($ new, $ i, 1) = lc (substr ($ new, $ i, 1));
$ bang = 1;
} Else {
substr ($ new, $ i, 1) = uc (substr ($ new, $ i, 1));
$ bang = 2;
}
}
# kết thúc với bất kỳ cái mới nào còn lại (khi cái mới lâu hơn cái cũ)
if ($ newlen> $ oldlen) {
if ($ state == 1) {
substr ($ new, $ oldlen) = lc (substr ($ new, $ oldlen));
} elsif ($ state == 2) {
substr ($ new, $ oldlen) = uc (substr ($ new, $ oldlen));
}
}
trả lại $ mới;
}

Làm thế nào có thể I làm cho "\ w" phù hợp với quốc gia tính cách bộ?
Đặt "sử dụng ngôn ngữ;" trong kịch bản của bạn. Lớp ký tự \ w được lấy từ ngôn ngữ hiện tại.

Xem perllocale để biết chi tiết.

Làm thế nào có thể I phù hợp với a ngôn ngữ thông minh phiên bản of "/ [a-zA-Z] /"?
Bạn có thể sử dụng cú pháp lớp ký tự POSIX "/ [[: alpha:]] /" được ghi bằng perlre.

Bất kể bạn ở ngôn ngữ nào, các ký tự chữ cái là các ký tự trong \ w
không có chữ số và gạch dưới. Dưới dạng regex, có dạng "/ [^ \ W \ d _] /". Nó là
phần bổ sung, không phải bảng chữ cái, sau đó là mọi thứ trong \ W cùng với các chữ số và
dấu gạch dưới hoặc "/ [\ W \ d _] /".

Làm thế nào có thể I trích dẫn a biến đến sử dụng in a biểu thức chính quy?
Trình phân tích cú pháp Perl sẽ mở rộng các tham chiếu $ variable và @variable trong các biểu thức chính quy
trừ khi dấu phân cách là một dấu ngoặc kép. Hãy nhớ rằng phía bên phải của
Thay thế "s ///" được coi là một chuỗi được trích dẫn kép (xem perlop để biết thêm chi tiết).
Ngoài ra, hãy nhớ rằng mọi ký tự đặc biệt regex sẽ được thực hiện trừ khi bạn đặt trước
thay thế bằng \ Q. Đây là một ví dụ:

$ string = "Placido P. Bạch tuộc";
$ regex = "P.";

$ string = ~ s / $ regex / Polyp /;
# $ string hiện là "Polypacido P. Octopus"

Tại vì "." là đặc biệt trong biểu thức chính quy và có thể khớp với bất kỳ ký tự đơn nào,
regex "P." ở đây đã khớp với trong chuỗi ban đầu.

Để thoát khỏi ý nghĩa đặc biệt của ".", Chúng tôi sử dụng "\ Q":

$ string = "Placido P. Bạch tuộc";
$ regex = "P.";

$ string = ~ s / \ Q $ regex / Polyp /;
# $ string hiện là "Placido Polyp Octopus"

Việc sử dụng "\ Q" làm cho dấu <.> Trong regex được coi như một ký tự thông thường, do đó
"P." khớp với "P" theo sau bởi một dấu chấm.

Điều gì is "/ o" có thật không cho?
(đóng góp bởi brian d foy)

Tùy chọn "/ o" cho các biểu thức chính quy (được ghi lại trong perlop và perlreref) cho Perl biết
chỉ biên dịch biểu thức chính quy một lần. Điều này chỉ hữu ích khi mẫu có chứa
Biến đổi. Perls 5.6 trở lên tự động xử lý điều này nếu mẫu không thay đổi.

Vì toán tử so khớp "m //", toán tử thay thế "s ///" và
toán tử trích dẫn biểu thức "qr //" là các cấu trúc kép quotish, bạn có thể nội suy
các biến vào mẫu. Xem câu trả lời cho "Làm cách nào để trích dẫn một biến để sử dụng trong
regex? "để biết thêm chi tiết.

Ví dụ này lấy một biểu thức chính quy từ danh sách đối số và in ra các dòng
đầu vào phù hợp với nó:

$ pattern = shift @ARGV của tôi;

trong khi (<>) {
in if m / $ pattern /;
}

Các phiên bản của Perl trước 5.6 sẽ biên dịch lại biểu thức chính quy cho mỗi lần lặp,
ngay cả khi $ pattern không thay đổi. "/ O" sẽ ngăn điều này bằng cách yêu cầu Perl biên dịch
mẫu lần đầu tiên, sau đó sử dụng lại mẫu đó cho các lần lặp tiếp theo:

$ pattern = shift @ARGV của tôi;

trong khi (<>) {
in if m / $ pattern / o; # hữu ích cho Perl <5.6
}

Trong các phiên bản 5.6 trở lên, Perl sẽ không biên dịch lại biểu thức chính quy nếu biến
không thay đổi, vì vậy bạn có thể không cần tùy chọn "/ o". Nó không đau, nhưng nó
cũng không giúp được gì. Nếu bạn muốn bất kỳ phiên bản Perl nào để biên dịch biểu thức chính quy
chỉ một lần ngay cả khi biến thay đổi (do đó, chỉ sử dụng giá trị ban đầu của nó), bạn vẫn
cần "/ o".

Bạn có thể xem công cụ biểu thức chính quy của Perl tại nơi làm việc để tự xác minh xem Perl có
biên dịch lại một biểu thức chính quy. Pragma "use re 'debug'" (đi kèm với Perl 5.005 và
sau) hiển thị các chi tiết. Với Perls trước 5.6, bạn sẽ thấy "lại" báo cáo rằng
biên dịch biểu thức chính quy trên mỗi lần lặp. Với Perl 5.6 trở lên, bạn nên
chỉ xem báo cáo "lại" cho lần lặp đầu tiên.

sử dụng re 'debug';

$ regex của tôi = 'Perl';
foreach (qw (Perl Java Ruby Python)) {
in STDERR "-" x 73, "\ n";
print STDERR "Đang thử $ _... \ n";
print STDERR "\ t $ _ is good! \ n" if m / $ regex /;
}

Làm thế nào do I sử dụng a đều đặn biểu hiện đến dải Phong cách C Bình luận từ a tập tin?
Mặc dù điều này thực sự có thể làm được, nhưng nó khó hơn bạn nghĩ rất nhiều. Ví dụ, điều này
lót

perl -0777 -pe 's {/\*.*?\*/} {} gs' foo.c

sẽ hoạt động trong nhiều trường hợp nhưng không phải tất cả các trường hợp. Bạn thấy đấy, nó quá đơn giản đối với một số loại
Đặc biệt, các chương trình C, những chương trình có vẻ như là chú thích trong các chuỗi được trích dẫn. Vì
rằng, bạn sẽ cần một cái gì đó như thế này, được tạo bởi Jeffrey Friedl và sau đó được sửa đổi bởi Fred
Curtis.

$ / = undef;
$ _ = <>;
s # / \ * [^ *] * \ * + ([^ / *] [^ *] * \ * +) * / | ("(\\. | [^" \\]) * "| '( \\. | [^ '\\]) *' |. [^ / "'\\] *) # đã định nghĩa $ 2? $ 2: "" #gse;
in;

Tất nhiên, điều này có thể được viết dễ hiểu hơn với công cụ sửa đổi "/ x", thêm khoảng trắng
và nhận xét. Ở đây nó được mở rộng, nhờ sự hỗ trợ của Fred Curtis.

s{
/ \ * ## Bắt đầu / * ... * / nhận xét
[^ *] * \ * + ## Non- * theo sau là 1 hoặc nhiều * s
(
[^ / *] [^ *] * \ * +
) * ## 0-hoặc nhiều thứ không bắt đầu bằng /
## nhưng kết thúc bằng '*'
/ ## End of / * ... * / comment

| ## HOẶC nhiều thứ khác nhau không phải là bình luận:

(
"## Bắt đầu chuỗi" ... "
(
\\. ## Ký tự thoát
| ## HOẶC
[^ "\\] ## Non" \
)*
"## Cuối chuỗi" ... "

| ## HOẶC

'## Bắt đầu chuỗi' ... '
(
\\. ## Ký tự thoát
| ## HOẶC
[^ '\\] ## Non' \
)*
'## End of' ... 'chuỗi

| ## HOẶC

. ## Bất kỳ char nào khác
[^ / "'\\] * ## Các ký tự không bắt đầu nhận xét, chuỗi hoặc thoát
)
} {đã định nghĩa $ 2? $ 2: ""} gxse;

Một sửa đổi nhỏ cũng loại bỏ các nhận xét C ++, có thể kéo dài nhiều dòng bằng cách sử dụng
nhân vật tiếp tục:

s # / \ * [^ *] * \ * + ([^ / *] [^ *] * \ * +) * / | // ([^ \\] | [^ \ n] [\ n]? ) *? \ n | ("(\\. | [^" \\]) * "| '(\\. | [^' \\]) * '|. [^ /"' \\] *) #defined $ 3? $ 3: "" #gse;

Có thể I sử dụng Perl đều đặn biểu thức đến phù hợp với cân bằng bản văn?
(đóng góp bởi brian d foy)

Lần thử đầu tiên của bạn có lẽ nên là mô-đun Text :: Balanced, theo tiêu chuẩn Perl
thư viện kể từ Perl 5.8. Nó có nhiều chức năng khác nhau để xử lý các văn bản khó. Các
Regexp :: Mô-đun chung cũng có thể trợ giúp bằng cách cung cấp các mẫu đóng hộp mà bạn có thể sử dụng.

Kể từ Perl 5.10, bạn có thể đối sánh văn bản cân bằng với các biểu thức chính quy bằng cách sử dụng đệ quy
các mẫu. Trước Perl 5.10, bạn phải dùng đến nhiều thủ thuật khác nhau như sử dụng mã Perl trong
trình tự "(?? {})".

Đây là một ví dụ sử dụng một biểu thức chính quy đệ quy. Mục tiêu là nắm bắt tất cả
văn bản trong dấu ngoặc nhọn, bao gồm văn bản trong dấu ngoặc nhọn lồng nhau. Văn bản mẫu này
có hai nhóm "chính": một nhóm có một cấp độ lồng vào nhau và một nhóm có hai cấp độ
làm tổ. Có tổng số năm nhóm trong dấu ngoặc nhọn:

tôi có một ít > và
>>
và đó là nó.

Biểu thức chính quy để khớp với văn bản cân bằng sử dụng hai hàm thông thường mới (cho Perl 5.10)
các tính năng biểu hiện. Chúng được bao phủ bởi perlre và ví dụ này là phiên bản sửa đổi của
một trong tài liệu đó.

Đầu tiên, việc thêm dấu "+" sở hữu mới vào bất kỳ bộ định lượng nào sẽ tìm thấy kết quả phù hợp dài nhất và thực hiện
không phải nhạc nền. Điều đó quan trọng vì bạn muốn xử lý bất kỳ dấu ngoặc nhọn nào thông qua
đệ quy, không quay lui. Nhóm "[^ <>] ++" tìm một hoặc nhiều dấu ngoặc nhọn
mà không cần bẻ khóa.

Thứ hai, "(? PARNO)" mới đề cập đến mẫu phụ trong nhóm bắt cụ thể đã cho
bởi "PARNO". Trong regex sau đây, nhóm chụp đầu tiên tìm thấy (và ghi nhớ)
văn bản cân bằng và bạn cần có cùng mẫu đó trong vùng đệm đầu tiên để vượt qua
văn bản lồng nhau. Đó là phần đệ quy. "(? 1)" sử dụng mẫu trong chụp bên ngoài
nhóm như một phần độc lập của regex.

Kết hợp tất cả lại với nhau, bạn có:

#! / usr / local / bin / perl5.10.0

$ string của tôi = << "TẠI ĐÂY";
tôi có một ít > và
>>
và đó là nó.
tại ĐÂY

@groups của tôi = $ string = ~ m /
(# đầu của nhóm chụp 1
<# khớp với một dấu ngoặc nhọn mở
(?:
[^ <>] ++ # một hoặc nhiều dấu ngoặc nhọn, không dấu ngoặc nhọn
|
(? 1) # found <hoặc>, vì vậy hãy đệ quy để nắm bắt nhóm 1
)*
> # khớp với một dấu ngoặc nhọn đóng
) # cuối nhóm chụp 1
/ xg;

$ "=" \ n \ t ";
print "Đã tìm thấy: \ n \ t @ groups \ n";

Kết quả cho thấy Perl đã tìm thấy hai nhóm chính:

tìm:
>
>>

Với một chút công việc bổ sung, bạn có thể nhận được tất cả các nhóm trong dấu ngoặc nhọn ngay cả khi chúng
trong các dấu ngoặc nhọn khác nữa. Mỗi khi bạn nhận được một kết hợp cân bằng, hãy loại bỏ lớp vỏ ngoài của nó
dấu phân tách (đó là dấu bạn vừa khớp để không khớp lại) và thêm nó vào hàng đợi
của chuỗi để xử lý. Tiếp tục làm điều đó cho đến khi bạn không nhận được kết quả phù hợp nào:

#! / usr / local / bin / perl5.10.0

@queue của tôi = << "TẠI ĐÂY";
tôi có một ít > và
>>
và đó là nó.
tại ĐÂY

$ regex = qr / của tôi
(# đầu dấu ngoặc 1
<# khớp với một dấu ngoặc nhọn mở
(?:
[^ <>] ++ # một hoặc nhiều dấu ngoặc nhọn, không dấu ngoặc nhọn
|
(? 1) # đệ quy thành dấu ngoặc 1
)*
> # khớp với một dấu ngoặc nhọn đóng
) # cuối dấu ngoặc 1
/NS;

$ "=" \ n \ t ";

trong khi (@queue) {
$ string = shift @queue của tôi;

@groups của tôi = $ string = ~ m / $ regex / g;
print "Đã tìm thấy: \ n \ t @ groups \ n \ n" if @groups;

unshift @queue, bản đồ {s / ^ $ //; $ _} @ nhóm;
}

Kết quả hiển thị tất cả các nhóm. Các kết quả phù hợp ngoài cùng hiển thị đầu tiên và các kết quả được lồng vào nhau
các trận đấu hiển thị sau:

tìm:
>
>>

tìm:


tìm:
>

tìm:


Điều gì làm it nghĩa là việc này biểu thức chính quy đang tham? Làm thế nào có thể I được xung quanh nó?
Hầu hết mọi người có nghĩa là các regex tham lam khớp càng nhiều càng tốt. Về mặt kỹ thuật,
nó thực sự là các bộ định lượng ("?", "*", "+", "{}") tham lam hơn là toàn bộ
mẫu; Perl thích lòng tham cục bộ và sự hài lòng tức thì hơn là lòng tham nói chung. Để có được
các phiên bản không tham lam của cùng một bộ định lượng, hãy sử dụng ("??", "*?", "+?", "{}?").

Một ví dụ:

my $ s1 = my $ s2 = "Tôi rất lạnh";
$ s1 = ~ s / ve. * y //; # Toi lanh
$ s2 = ~ s / ve. *? y //; # Tôi rất lạnh

Lưu ý cách thay thế thứ hai ngừng khớp ngay khi nó gặp "y". Các
"*?" bộ định lượng thông báo một cách hiệu quả cho công cụ biểu thức chính quy để tìm một kết quả phù hợp một cách nhanh chóng
càng tốt và chuyển quyền kiểm soát cho bất kỳ thứ gì ở dòng tiếp theo, như bạn sẽ làm nếu bạn
chơi khoai tây nóng.

Làm thế nào do I quá trình mỗi lời on mỗi hàng?
Sử dụng chức năng tách:

trong khi (<>) {
nói trước $ word của tôi (tách ra) {
# làm điều gì đó với $ word tại đây
}
}

Lưu ý rằng đây không thực sự là một từ theo nghĩa tiếng Anh; nó chỉ là những phần liên tiếp
các ký tự không có khoảng trắng.

Để chỉ làm việc với các chuỗi chữ và số (bao gồm cả dấu gạch dưới), bạn có thể cân nhắc

trong khi (<>) {
foreach $ word (m / (\ w +) / g) {
# làm điều gì đó với $ word tại đây
}
}

Làm thế nào có thể I in ra a tần số từ or tần số dòng tóm lược?
Để làm điều này, bạn phải phân tích cú pháp từng từ trong luồng đầu vào. Chúng tôi sẽ giả vờ điều đó bằng cách
từ bạn có nghĩa là một phần của bảng chữ cái, dấu gạch nối hoặc dấu nháy đơn, thay vì
ý tưởng phân đoạn khoảng trắng của một từ được đưa ra trong câu hỏi trước:

của tôi (% đã xem);
trong khi (<>) {
while (/ (\ b [^ \ W_ \ d] [\ w '-] + \ b) / g) {# bỏ lỡ "` cừu' "
$ đã thấy {$ 1} ++;
}
}

trong khi (của tôi ($ word, $ count) = mỗi% đã xem) {
print "$ count $ word \ n";
}

Nếu bạn muốn làm điều tương tự cho các dòng, bạn sẽ không cần biểu thức chính quy:

của tôi (% đã xem);

trong khi (<>) {
$ đã thấy {$ _} ++;
}

trong khi (của tôi ($ dòng, $ count) = mỗi% đã thấy) {
print "$ count $ line";
}

Nếu bạn muốn các đầu ra này theo thứ tự đã sắp xếp, hãy xem perlfaq4: "Làm cách nào để sắp xếp một hàm băm
(tùy chọn theo giá trị thay vì khóa)? ”.

Làm thế nào có thể I do gần đúng phù hợp?
Xem chuỗi mô-đun :: Khoảng có sẵn từ CPAN.

Làm thế nào do I hiệu quả phù hợp với nhiều đều đặn biểu thức at Một lần?
(đóng góp bởi brian d foy)

Nếu bạn có Perl 5.10 hoặc mới hơn, điều này gần như không đáng kể. Bạn chỉ phù hợp thông minh với một
mảng các đối tượng biểu thức chính quy:

my @patterns = (qr / Fr.d /, qr / B.rn.y /, qr / W.lm. /);

if ($ string ~~ @patterns) {
...
};

Kết hợp thông minh dừng khi tìm thấy kết quả phù hợp, vì vậy nó không cần phải thử mọi biểu thức.

Sớm hơn Perl 5.10, bạn có một chút việc phải làm. Bạn muốn tránh biên dịch
biểu thức chính quy mỗi khi bạn muốn đối sánh nó. Trong ví dụ này, perl phải biên dịch lại
biểu thức chính quy cho mỗi lần lặp lại của vòng lặp "foreach" vì nó không có cách nào để
biết $ pattern sẽ là gì:

my @patterns = qw (foo bar baz);

LINE: trong khi ( ) {
foreach $ pattern (@patterns) {
if (/ \ b $ pattern \ b / i) {
in;
hàng tiếp theo;
}
}
}

Toán tử "qr //" được hiển thị trong perl 5.005. Nó biên dịch một biểu thức chính quy, nhưng không
áp dụng nó. Khi bạn sử dụng phiên bản được biên dịch trước của regex, perl hoạt động ít hơn. Trong này
ví dụ, tôi đã chèn một "bản đồ" để biến mỗi mẫu thành dạng được biên dịch trước. Phần còn lại của
tập lệnh giống nhau, nhưng nhanh hơn:

my @patterns = map {qr / \ b $ _ \ b / i} qw (foo bar baz);

LINE: while (<>) {
foreach $ pattern (@patterns) {
if (/ $ pattern /) {
in;
hàng tiếp theo;
}
}
}

Trong một số trường hợp, bạn có thể tạo một số mẫu thành một biểu thức chính quy.
Hãy cẩn thận với các tình huống yêu cầu backtracking.

my $ regex = tham gia '|', qw (foo bar baz);

LINE: while (<>) {
in if / \ b (?: $ regex) \ b / i;
}

Để biết thêm chi tiết về hiệu quả của biểu thức chính quy, hãy xem Làm chủ Đều đặn Biểu thức by
Jeffrey Friedl. Anh ấy giải thích cách hoạt động của công cụ biểu thức chính quy và lý do tại sao một số mẫu
không hiệu quả một cách đáng ngạc nhiên. Khi bạn hiểu cách perl áp dụng các biểu thức chính quy,
bạn có thể điều chỉnh chúng cho các tình huống riêng lẻ.

Tại sao không Ranh giới từ tìm kiếm với "\NS" công việc cho tôi?
(đóng góp bởi brian d foy)

Đảm bảo rằng bạn biết \ b thực sự làm gì: đó là ranh giới giữa một ký tự từ, \ w,
và một cái gì đó không phải là một ký tự từ. Điều đó không phải là một ký tự từ có thể là
\ W, nhưng nó cũng có thể là đầu hoặc cuối của chuỗi.

Đó không phải (không phải!) Ranh giới giữa khoảng trắng và không khoảng trắng, và nó không phải là thứ
giữa các từ chúng ta sử dụng để tạo câu.

Trong regex speak, ranh giới từ (\ b) là "xác nhận độ rộng bằng không", nghĩa là nó không
đại diện cho một ký tự trong chuỗi, nhưng một điều kiện ở một vị trí nhất định.

Đối với biểu thức chính quy, / \ bPerl \ b /, phải có một ranh giới từ trước "P" và
sau chữ "l". Miễn là một cái gì đó không phải là một ký tự từ đứng trước "P" và
thành công chữ "l", mẫu sẽ khớp. Các chuỗi này khớp với / \ bPerl \ b /.

"Perl" # không có ký tự từ nào trước P hoặc sau l
"Perl" # giống như trước (khoảng trắng không phải là ký tự từ)
"Perl" "# the 'char không phải là một từ char
"Perl's" # không có ký tự từ nào trước P, ký tự không phải từ sau "l"

Các chuỗi này không khớp với / \ bPerl \ b /.

"Perl_" # _ là một từ char!
"Perler" # không có ký tự từ nào trước P, nhưng một ký tự sau l

Tuy nhiên, bạn không cần phải sử dụng \ b để nối các từ. Bạn có thể tìm các ký tự không phải từ
được bao quanh bởi các ký tự từ. Các chuỗi này khớp với mẫu / \ b '\ b /.

"đừng" # ký tự 'được bao quanh bởi "n" và "t"
"qep'a '" # the' char được bao quanh bởi "p" và "a"

Các chuỗi này không khớp với / \ b '\ b /.

"foo '" # không có từ char sau không phải từ'

Bạn cũng có thể sử dụng phần bổ sung của \ b, \ B, để chỉ định rằng không nên có một từ
ranh giới.

Trong mẫu / \ Bam \ B /, phải có một ký tự từ trước "a" và sau "m".
Các mẫu này khớp với / \ Bam \ B /:

"llama" # "am" được bao quanh bởi các ký tự từ
"Samuel" # giống nhau

Các chuỗi này không khớp / \ Bam \ B /

"Sam" # không có ranh giới từ trước "a", nhưng một sau "m"
"Tôi là Sam" # "am" được bao quanh bởi các ký tự không phải từ

Tại sao làm sử dụng $ &, $ `, or $' chậm my chương trình xuống?
(do Anno Siegel đóng góp)

Khi Perl thấy rằng bạn cần một trong những biến này ở bất kỳ đâu trong chương trình, nó sẽ cung cấp
chúng trên mỗi và mọi mẫu phù hợp. Điều đó có nghĩa là trên mỗi mẫu phù hợp với toàn bộ
chuỗi sẽ được sao chép, một phần thành $ `, một phần thành $ &, và một phần thành $ '. Như vậy hình phạt là
nghiêm trọng nhất với các dây dài và các mẫu phù hợp thường xuyên. Tránh $ &, $ 'và $ `nếu bạn
có thể, nhưng nếu bạn không thể, một khi bạn đã sử dụng chúng, hãy sử dụng chúng theo ý muốn vì bạn
đã trả giá. Hãy nhớ rằng một số thuật toán thực sự đánh giá cao chúng. Kể từ
5.005 phát hành, biến $ & không còn "đắt" như hai biến kia.

Vì Perl 5.6.1, các biến đặc biệt @ - và @ + có thể thay thế chức năng $ `, $ & và $ '.
Các mảng này chứa các con trỏ đến đầu và cuối của mỗi trận đấu (xem perlvar để biết
đầy đủ câu chuyện), vì vậy họ cung cấp cho bạn thông tin về cơ bản giống nhau, nhưng không có rủi ro
sao chép chuỗi quá mức.

Perl 5.10 đã thêm ba điểm đặc biệt, "$ {^ MATCH}", "$ {^ PREMATCH}" và "$ {^ POSTMATCH}" để thực hiện
cùng một công việc nhưng không có hình phạt hiệu suất toàn cầu. Perl 5.10 chỉ đặt các biến này
nếu bạn biên dịch hoặc thực thi biểu thức chính quy với sửa đổi "/ p".

Điều gì tốt is "\NS" in a đều đặn biểu hiện?
Bạn sử dụng ký tự liên kết "\ G" để bắt đầu trận đấu tiếp theo trên cùng một chuỗi mà trận đấu cuối cùng
rời khỏi. Công cụ biểu thức chính quy không thể bỏ qua bất kỳ ký tự nào để tìm ký tự tiếp theo
khớp với ký tự liên kết này, vì vậy "\ G" tương tự như phần đầu của ký tự liên kết chuỗi, "^". Các
Anchor "\ G" thường được sử dụng với cờ "g". Nó sử dụng giá trị của "pos ()" làm
vị trí để bắt đầu trận đấu tiếp theo. Khi người điều hành trận đấu thực hiện các trận đấu liên tiếp, nó
cập nhật "pos ()" với vị trí của ký tự tiếp theo trong trận đấu cuối cùng (hoặc ký tự đầu tiên
nhân vật của trận đấu tiếp theo, tùy thuộc vào cách bạn thích nhìn vào nó). Mỗi chuỗi có
riêng giá trị "pos ()".

Giả sử bạn muốn so khớp tất cả các cặp chữ số liên tiếp trong một chuỗi như "1122a44"
và dừng đối sánh khi bạn gặp các chữ số không phải. Bạn muốn so khớp 11 và 22 nhưng
chữ cái hiển thị trong khoảng từ 22 đến 44 và bạn muốn dừng lại ở "a". Đơn giản chỉ cần kết hợp các cặp
trong số các chữ số bỏ qua "a" và vẫn khớp với 44.

$ _ = "1122a44";
của tôi @pairs = m / (\ d \ d) / g; # qw (11 22 44)

Nếu bạn sử dụng ký tự liên kết "\ G", bạn buộc đối sánh sau 22 phải bắt đầu bằng ký tự "a". Các
biểu thức chính quy không thể khớp ở đó vì nó không tìm thấy một chữ số, vì vậy, kết quả phù hợp tiếp theo
không thành công và toán tử đối sánh trả về các cặp mà nó đã tìm thấy.

$ _ = "1122a44";
my @pairs = m / \ G (\ d \ d) / g; # qw (11 22)

Bạn cũng có thể sử dụng ký tự liên kết "\ G" trong ngữ cảnh vô hướng. Bạn vẫn cần cờ "g".

$ _ = "1122a44";
trong khi (m / \ G (\ d \ d) / g) {
print "Đã tìm thấy $ 1 \ n";
}

Sau khi trận đấu không thành công ở ký tự "a", perl đặt lại "pos ()" và kết quả phù hợp tiếp theo trên
cùng một chuỗi bắt đầu ở đầu.

$ _ = "1122a44";
trong khi (m / \ G (\ d \ d) / g) {
print "Đã tìm thấy $ 1 \ n";
}

print "Tìm thấy $ 1 sau while" if m / (\ d \ d) / g; # tìm thấy "11"

Bạn có thể tắt đặt lại "pos ()" khi không thành công với cờ "c", được ghi lại trong perlop và
perlreref. Các trận đấu tiếp theo bắt đầu khi trận đấu thành công cuối cùng kết thúc (giá trị của
"pos ()") ngay cả khi đối sánh trên cùng một chuỗi không thành công trong thời gian chờ đợi. Trong trường hợp này,
khớp sau vòng lặp "while ()" bắt đầu tại "a" (nơi trận đấu cuối cùng dừng lại) và kể từ
nó không sử dụng bất kỳ mỏ neo nào nó có thể bỏ qua "a" để tìm 44.

$ _ = "1122a44";
trong khi (m / \ G (\ d \ d) / gc) {
print "Đã tìm thấy $ 1 \ n";
}

print "Tìm thấy $ 1 sau while" if m / (\ d \ d) / g; # tìm thấy "44"

Thông thường, bạn sử dụng liên kết "\ G" với cờ "c" khi bạn muốn thử một kết hợp khác
nếu một lỗi không thành công, chẳng hạn như trong một tokenizer. Jeffrey Friedl đưa ra ví dụ này hoạt động trong
5.004 trở lên.

trong khi (<>) {
nhai;
BỘ PHẬN: {
m / \ G (\ d + \ b) / gcx && do {print "number: $ 1 \ n"; làm lại; };
m / \ G (\ w +) / gcx && do {print "word: $ 1 \ n"; làm lại; };
m / \ G (\ s +) / gcx && do {print "space: $ 1 \ n"; làm lại; };
m / \ G ([^ \ w \ d] +) / gcx && do {print "other: $ 1 \ n"; làm lại; };
}
}

Đối với mỗi dòng, vòng lặp "PARSER" trước tiên cố gắng khớp một chuỗi các chữ số theo sau là
Ranh giới từ. Trận đấu này phải bắt đầu tại vị trí mà trận đấu cuối cùng đã kết thúc (hoặc
đầu của chuỗi trên trận đấu đầu tiên). Vì "m / \ G (\ d + \ b) / gcx" sử dụng cờ "c",
nếu chuỗi không khớp với biểu thức chính quy đó, perl không đặt lại pos ()
trận đấu tiếp theo bắt đầu ở cùng một vị trí để thử một mẫu khác.

Perl biểu thức chính quy DFA or NFA? họ POSIX tuân thủ?
Mặc dù đúng là biểu thức chính quy của Perl giống với DFA (hữu hạn xác định
tự động) của ví dụ(1) chương trình, chúng trên thực tế được triển khai dưới dạng NFA (không xác định
dữ liệu tự động hữu hạn) để cho phép backtracking và backreferencing. Và chúng không theo kiểu POSIX
bởi vì những điều đó đảm bảo hành vi trong trường hợp xấu nhất cho mọi trường hợp. (Có vẻ như một số
mọi người thích đảm bảo tính nhất quán, ngay cả khi điều được đảm bảo là sự chậm chạp.) Xem phần
cuốn sách "Làm chủ Biểu thức Thông thường" (từ O'Reilly) của Jeffrey Friedl để biết tất cả các chi tiết
bạn có thể hy vọng biết về những vấn đề này (trích dẫn đầy đủ xuất hiện trong perlfaq2).

Có gì sai với sử dụng grep in a làm mất hiệu lực định nghĩa bài văn?
Vấn đề là grep xây dựng một danh sách trả về, bất kể ngữ cảnh. Điều này có nghĩa là
bạn đang khiến Perl gặp rắc rối trong việc xây dựng một danh sách mà sau đó bạn chỉ cần vứt bỏ. Nếu như
danh sách lớn, bạn lãng phí cả thời gian và không gian. Nếu mục đích của bạn là lặp lại
danh sách, sau đó sử dụng vòng lặp for cho mục đích này.

Trong các perls cũ hơn 5.8.1, bản đồ cũng gặp phải vấn đề này. Nhưng kể từ ngày 5.8.1, điều này
đã được sửa và bản đồ nhận biết ngữ cảnh - trong ngữ cảnh trống, không có danh sách nào được xây dựng.

Làm thế nào có thể I phù hợp với dây với nhiều byte nhân vật?
Bắt đầu từ Perl 5.6 Perl đã có một số cấp độ hỗ trợ ký tự đa byte. Perl 5.8 hoặc
sau đó được khuyến khích. Các tiết mục ký tự nhiềubyte được hỗ trợ bao gồm Unicode, và
mã hóa kế thừa thông qua mô-đun Mã hóa. Xem perluniintro, perlunicode và Encode.

Nếu bạn gặp khó khăn với các Perls cũ hơn, bạn có thể thực hiện Unicode với mô-đun Unicode :: String, và
chuyển đổi ký tự bằng cách sử dụng mô-đun Unicode :: Map8 và Unicode :: Bản đồ. Nếu bạn đang sử dụng
Bảng mã tiếng Nhật, bạn có thể thử sử dụng jperl 5.005_03.

Cuối cùng, nhóm phương pháp tiếp cận sau đây được đưa ra bởi Jeffrey Friedl, người có bài báo trong
số 5 của Tạp chí Perl nói về vấn đề này.

Giả sử bạn có một số mã hóa sao Hỏa kỳ lạ trong đó các cặp chữ cái viết hoa ASCII
mã hóa các chữ cái sao Hỏa đơn lẻ (tức là hai byte "CV" tạo thành một chữ cái sao Hỏa duy nhất, như vậy
hai byte "SG", "VS", "XX", v.v.). Các byte khác đại diện cho các ký tự đơn lẻ, giống như
ASCII.

Vì vậy, chuỗi của người sao Hỏa "Tôi là CVSGXX!" sử dụng 12 byte để mã hóa chín ký tự 'I',
'', 'a', 'm', '', 'CV', 'SG', 'XX', '!'.

Bây giờ, giả sử bạn muốn tìm kiếm ký tự đơn "/ GX /". Perl không biết về
Sao Hỏa, vì vậy nó sẽ tìm thấy hai byte "GX" trong "Tôi là CVSGXX!" chuỗi, mặc dù điều đó
không có nhân vật ở đó: có vẻ như đó là vì "SG" nằm cạnh "XX", nhưng có
không có "GX" thực. Đây là một vấn đề lớn.

Dưới đây là một số cách, tất cả đều khó khăn, để đối phó với nó:

# Đảm bảo rằng các byte "martian" liền kề không còn liền kề.
$ martian = ~ s / ([AZ] [AZ]) / $ 1 / g;

print "found GX! \ n" if $ martian = ~ / GX /;

Hoặc như thế này:

@chars của tôi = $ martian = ~ m / ([AZ] [AZ] | [^ AZ]) / g;
# ở trên tương tự về mặt khái niệm với: my @chars = $ text = ~ m /(.)/ g;
#
nói trước $ char (@chars) của tôi {
print "found GX! \ n", last if $ char eq 'GX';
}

Hoặc như thế này:

while ($ martian = ~ m / \ G ([AZ] [AZ] |.) / gs) {# \ G có thể không cần thiết
if ($ 1 eq 'GX') {
print "GX tìm thấy! \ n";
Cuối cùng;
}
}

Đây là một cách khác, ít đau hơn một chút, để làm điều đó từ Benjamin Goldberg, người sử dụng
khẳng định nhìn lại phía sau phủ định bằng không chiều rộng.

in "GX tìm thấy! \ n" nếu $ martian = ~ m /
(?
(?: [AZ] [AZ]) *?
GX
/NS;

Điều này thành công nếu ký tự "sao hỏa" GX có trong chuỗi và không thành công nếu không. nếu bạn
không thích sử dụng (?
(?

Nó có nhược điểm là đặt sai $ - [0] và $ + [0], nhưng điều này thường
có thể được làm việc xung quanh.

Làm thế nào do I phù hợp với a đều đặn biểu hiện đó là in a Biến đổi?
(đóng góp bởi brian d foy)

Chúng ta không cần phải nhập các mẫu mã cố định vào toán tử đối sánh (hoặc bất kỳ thứ gì khác hoạt động
với biểu thức chính quy). Chúng ta có thể đặt mẫu vào một biến để sử dụng sau này.

Toán tử đối sánh là một ngữ cảnh trích dẫn kép, vì vậy bạn có thể nội suy biến của mình chỉ
giống như một chuỗi được trích dẫn kép. Trong trường hợp này, bạn đọc biểu thức chính quy dưới dạng đầu vào của người dùng
và lưu trữ nó trong $ regex. Khi bạn có mẫu trong $ regex, bạn sử dụng biến đó trong
toán tử đối sánh.

chomp ($ regex của tôi = );

if ($ string = ~ m / $ regex /) {...}

Mọi ký tự đặc biệt của biểu thức chính quy trong $ regex vẫn là đặc biệt và mẫu
vẫn phải hợp lệ nếu không Perl sẽ khiếu nại. Ví dụ, trong mẫu này có một
dấu ngoặc đơn không ghép đôi.

my $ regex = "Chưa khớp (dấu ngoặc";

"Hai parens để ràng buộc tất cả" = ~ m / $ regex /;

Khi Perl biên dịch biểu thức chính quy, nó coi dấu ngoặc đơn là phần bắt đầu của một
trận đấu trí nhớ. Khi nó không tìm thấy dấu ngoặc đơn, nó phàn nàn:

Chưa khớp (trong regex; được đánh dấu bằng <- HERE trong m / Chưa khớp (dấu <- HERE / tại dòng chữ 3).

Bạn có thể giải quyết vấn đề này bằng một số cách tùy thuộc vào tình huống của chúng ta. Đầu tiên, nếu bạn không
muốn bất kỳ ký tự nào trong chuỗi trở nên đặc biệt, bạn có thể thoát chúng bằng
"quotemeta" trước khi bạn sử dụng chuỗi.

chomp ($ regex của tôi = );
$ regex = quotemeta ($ regex);

if ($ string = ~ m / $ regex /) {...}

Bạn cũng có thể thực hiện điều này trực tiếp trong toán tử so khớp bằng cách sử dụng chuỗi "\ Q" và "\ E". Các
"\ Q" cho Perl biết nơi bắt đầu thoát các ký tự đặc biệt và "\ E" cho Perl biết nơi cần
dừng lại (xem perlop để biết thêm chi tiết).

chomp ($ regex của tôi = );

if ($ string = ~ m / \ Q $ regex \ E /) {...}

Ngoài ra, bạn có thể sử dụng "qr //", toán tử trích dẫn biểu thức chính quy (xem perlop để biết
chi tiết hơn). Nó trích dẫn và có lẽ biên dịch mẫu, và bạn có thể áp dụng
cờ biểu hiện cho mẫu.

chomp ($ input của tôi = );

của tôi $ regex = qr / $ input / is;

$ string = ~ m / $ regex / # giống như m / $ input / is;

Bạn cũng có thể muốn bẫy bất kỳ lỗi nào bằng cách bọc một khối "eval" xung quanh toàn bộ.

chomp ($ input của tôi = );

đánh giá {
if ($ string = ~ m / \ Q $ input \ E /) {...}
};
cảnh báo $ @ nếu $ @;

Hoặc là...

my $ regex = eval {qr / $ input / is};
if (đã định nghĩa $ regex) {
$ string = ~ m / $ regex /;
}
khác {
cảnh báo $ @;
}

TÁC GIẢ BẢN QUYỀN


Bản quyền (c) 1997-2010 Tom Christiansen, Nathan Torkington, và các tác giả khác như đã lưu ý.
Tất cả quyền được bảo lưu.

Tài liệu này là miễn phí; bạn có thể phân phối lại nó và / hoặc sửa đổi nó theo các điều khoản tương tự
như chính Perl.

Bất kể phân phối của nó, tất cả các ví dụ mã trong tệp này theo đây được đặt vào
miền công cộng. Bạn được phép và khuyến khích sử dụng mã này trong các chương trình của riêng bạn
để giải trí hoặc vì lợi nhuận khi bạn thấy phù hợp. Một nhận xét đơn giản trong mã cung cấp tín dụng sẽ là
nhã nhặn nhưng không bắt buộc.

Sử dụng perlfaq6 trực tuyến bằng các dịch vụ onworks.net


Máy chủ & Máy trạm miễn phí

Tải xuống ứng dụng Windows & Linux

  • 1
    Psi
    Psi
    Psi là XMPP mạnh mẽ đa nền tảng
    khách hàng được thiết kế cho người dùng có kinh nghiệm.
    Có sẵn các bản dựng dành cho MS
    Windows, GNU/Linux và macOS.. Đối tượng:
    Người dùng cuối...
    Tải xuống Psi
  • 2
    Blobby vô-lê 2
    Blobby vô-lê 2
    Tiếp nối chính thức của nổi tiếng
    Trò chơi điện tử Blobby Volley 1.x..
    Đối tượng: Người dùng cuối / Máy tính để bàn. Người sử dụng
    giao diện: OpenGL, SDL. Lập trình
    Ngôn ngữ: C++, Lua. C...
    Tải xuống Blobby Volley 2
  • 3
    SuiteCRM
    SuiteCRM
    SuiteCRM là Khách hàng từng đoạt giải thưởng
    Quản lý mối quan hệ (CRM)
    ứng dụng do tác giả mang đến cho bạn
    và người bảo trì, SalesAgility. Nó là
    thế giới ...
    Tải xuống SuiteCRM
  • 4
    quản trị viên quyền lực
    quản trị viên quyền lực
    Poweradmin là một DNS dựa trên web
    công cụ quản trị cho máy chủ PowerDNS.
    Giao diện có hỗ trợ đầy đủ cho hầu hết
    các tính năng của PowerDNS. Nó có đầy đủ
    ủng hộ...
    Tải xuống Poweradmin
  • 5
    Khung Web Gin
    Khung Web Gin
    Gin là một web framework cực kỳ nhanh
    được viết bằng Golang có thể thực hiện tối đa
    Nhanh hơn 40 lần, nhờ vào
    API giống martini và phiên bản tùy chỉnh của
    httprout ...
    Tải xuống Gin Web Framework
  • 6
    CEREUS LINUX
    CEREUS LINUX
    CEREUS LINUX dựa trên MX LINUX với
    nhiều loại khác nhau của các bản ghi. Đây là
    một ứng dụng cũng có thể được tìm nạp
    từ
    https://sourceforge.net/projects/cereu...
    Tải xuống CEREUS LINUX
  • Khác »

Lệnh Linux

  • 1
    abl
    abl
    abl - Đại diện tiền tố cho
    các hàm boolean MÔ TẢ:
    libablmmm.a là một thư viện cho phép
    biểu diễn hàm boolean trong một
    Dạng giống LISP. MỘT ...
    Chạy abl
  • 2
    một quyển sách
    một quyển sách
    tàu - chương trình sổ địa chỉ dựa trên văn bản
    ...
    Chạy sách
  • 3
    coqchk.opt
    coqchk.opt
    coqchk - Trình kiểm tra bằng chứng Coq được biên dịch
    người xác minh thư viện ...
    Chạy coqchk.opt
  • 4
    coqdep
    coqdep
    coqdep - Tính toán liên mô-đun
    phụ thuộc cho các chương trình Coq và Caml ...
    Chạy coqdep
  • 5
    trang web
    trang web
    ftangle,fweave - Bộ xử lý WEB cho C,
    C ++, Fortran, Ratfor và TeX ...
    Chạy fweb
  • 6
    bánh rán
    bánh rán
    quay tự do � nhạc kịch vòng lặp trực tiếp
    dụng cụ ...
    Chạy fweelin
  • Khác »

Ad