Làm cách nào tôi có thể chuyển đổi các biểu thức ereg thành preg trong PHP?


140

Do các biểu thức chính quy POSIX (ereg) không được dùng kể từ PHP 5.3.0, nên tôi muốn biết một cách dễ dàng để chuyển đổi các biểu thức cũ thành PCRE (Biểu thức chính quy tương thích Perl) (preg) .

Ví dụ, tôi có biểu thức chính quy này:

eregi('^hello world');

Làm cách nào tôi có thể dịch biểu thức thành preg_matchbiểu thức tương thích?

Lưu ý: Bài đăng này đóng vai trò giữ chỗ cho tất cả các bài đăng liên quan đến chuyển đổi từ ereg sang preg và dưới dạng tùy chọn trùng lặp cho các câu hỏi liên quan. Xin đừng đóng câu hỏi này.

Liên quan:


2
@ yes123: Vâng, đó là điểm chính, tôi cũng mệt mỏi vì điều đó. Tôi muốn một bài viết wiki thực sự giải thích một cái gì đó để chúng ta có thể đóng tất cả các câu hỏi cá nhân này.
netcoder

Tôi nghĩ rằng không cần điều này bởi vì bạn chỉ cần bọc cái cũ bằng một dấu phân cách. Ngoài ra tôi nghĩ rằng bạn có thể đã sử dụng một câu hỏi trả lời trước cho điều này.
năng động

Ah, đã bỏ phiếu cho một đóng trước khi đọc các ý kiến. Là một người giữ chỗ, nó có thể phục vụ một mục đích, nhưng không có câu hỏi cũ nào khác có thể phục vụ như vậy sao?
Wrikken

Hmm, thực sự. ereg [php]không mang lại rất nhiều kết quả hữu ích. OK, có thể cho tôi mượn hỗ trợ này.
Wrikken

8
Các bạn, dường như chúng ta gần như đã tạo ra một vòng các câu hỏi đóng về chủ đề này, tất cả đều chỉ vào nhau. Với tốc độ này, tất cả họ sẽ bị đóng cửa :)
Kev

Câu trả lời:


142

Sự thay đổi lớn nhất trong cú pháp là việc thêm các dấu phân cách .

ereg('^hello', $str);
preg_match('/^hello/', $str);

Dấu phân cách có thể là khá nhiều thứ không phải là số alpha, dấu gạch chéo ngược hoặc ký tự khoảng trắng. Được sử dụng nhiều nhất nói chung ~, /#.

Bạn cũng có thể sử dụng dấu ngoặc phù hợp:

preg_match('[^hello]', $str);
preg_match('(^hello)', $str);
preg_match('{^hello}', $str);
// etc

Nếu dấu phân cách của bạn được tìm thấy trong biểu thức chính quy, bạn phải thoát nó:

ereg('^/hello', $str);
preg_match('/^\/hello/', $str);

Bạn có thể dễ dàng thoát tất cả các dấu phân cách và ký tự dành riêng trong một chuỗi bằng cách sử dụng preg_quote :

$expr = preg_quote('/hello', '/');
preg_match('/^'.$expr.'/', $str);

Ngoài ra, PCRE hỗ trợ sửa đổi cho những thứ khác nhau. Một trong những ứng dụng được sử dụng nhiều nhất là công cụ sửa đổi không phân biệt chữ hoa chữ thường i, thay thế cho eregi :

eregi('^hello', 'HELLO');
preg_match('/^hello/i', 'HELLO');

Bạn có thể tìm thấy tài liệu tham khảo đầy đủ về cú pháp PCRE trong PHP trong hướng dẫn , cũng như một danh sách các khác biệt giữa regex POSIX và PCRE để giúp chuyển đổi biểu thức.

Tuy nhiên, trong ví dụ đơn giản của bạn, bạn sẽ không sử dụng biểu thức chính quy:

stripos($str, 'hello world') === 0

2
Giải thích tuyệt vời! Tôi chỉ muốn thêm một trường hợp đặc biệt trong đó bạn đang chuyển đổi từ ereg sang preg_match và bạn chỉ cần thoát các ký tự phân cách và không dành riêng các ký tự (vì chúng đã hoạt động như các ký tự đặc biệt, chúng tôi không muốn thoát chúng) : preg_match ('/'. str numplace ('/', '\ /', $ expr). '/', $ str);
Lolito

Điều đặc biệt đáng chú ý là nếu bạn sử dụng dấu ngoặc phù hợp, thì bạn không cần phải thoát bất kỳ ký tự nào "chỉ vì nó giống với dấu phân cách" giống như bạn làm với các biểu tượng khác như /^\/hello/ví dụ. (a(b)c)là một PCRE hoàn toàn hợp lệ, được phân định. Cá nhân tôi thích sử dụng dấu ngoặc đơn ()để nhắc nhở bản thân rằng trận đấu được bắt đầu tiên là toàn bộ.
Niet the Dark Absol

Tôi có thể nói, tôi rất ghét PHP! (Chỉ vậy thôi. Không có gì khác.) Tôi phải tìm kiếm những câu trả lời này khi máy chủ lưu trữ web được chia sẻ của tôi được cập nhật lên phiên bản mới và error_logs đầy đủ với những cảnh báo này : PHP Deprecated: Function ereg() is deprecated in.... Argh!
c00000fd

Làm thế nào để chuyển đổi này? $ regex = $ e. '((\. [^ \.'. $ E. '] [^'. $ E. '] *) | (\. \. [^'. $ E. '] +) | ([^ \. ] [^ '. $ e.'] *)) '. $ e. '\. \.' . $ e; để preg_math nó hoạt động tốt nhất bằng cách thêm / sửa đổi /
bdalina

32

Thay thế Ereg bằng preg (kể từ PHP 5.3.0) là bước đi đúng đắn có lợi cho chúng tôi.

preg_match, sử dụng cú pháp biểu thức chính quy tương thích Perl, thường là một thay thế nhanh hơn cho ereg.

Bạn nên biết 4 điều chính để chuyển mẫu ereg sang preg:

  1. Thêm dấu phân cách (/):'pattern' => '/pattern/'

  2. Dấu phân cách thoát nếu nó là một phần của mẫu: 'patt/ern' => '/patt\/ern/'
    Đạt được nó theo chương trình theo cách sau:
    $old_pattern = '<div>.+</div>';
    $new_pattern = '/' . addcslashes($old_pattern, '/') . '/';

  3. eregi (khớp không phân biệt chữ hoa chữ thường): 'pattern' => '/pattern/i' Vì vậy, nếu bạn đang sử dụng hàm eregi cho khớp không phân biệt chữ hoa chữ thường , chỉ cần thêm 'i' vào cuối mẫu mới ('/ mẫu /').

  4. Giá trị ASCII : Trong ereg, nếu bạn sử dụng số trong mẫu, có thể giả định rằng bạn đang đề cập đến ASCII của một ký tự. Nhưng trong preg, số không được coi là giá trị ASCII. Vì vậy, nếu mẫu của bạn chứa giá trị ASCII trong biểu thức ereg (ví dụ: dòng mới, tab, v.v.) thì hãy chuyển đổi nó thành thập lục phân và tiền tố với \ x.
    Example: 9(tab) becomes \x9 or alternatively use \t.


8

Từ phiên bản PHP 5.3, eregkhông được dùng nữa.

Chuyển từ eregsang preg_matchchỉ là một thay đổi nhỏ trong mô hình của chúng tôi.

Đầu tiên, bạn phải thêm dấu phân cách vào mã của mình, ví dụ:

ereg('A-Z0-9a-z', 'string');

đến

preg_match('/A-Z0-9a-z/', 'string');

Đối với kết eregihợp không phân biệt chữ hoa chữ thường, đặt isau dấu phân cách cuối cùng, ví dụ:

eregi('pattern', 'string');

đến

preg_match ('/pattern/i', 'string');

7

Có nhiều sự khác biệt giữa ereg()preg_replace()hơn chỉ là cú pháp:

  • Giá trị trả về:

    • Lỗi : cả hai trả lạiFALSE
    • Không có kết quả : ereg()trả lại FALSE, preg_match()trả lại0
    • Khi khớp : ereg()trả về độ dài chuỗi hoặc 1, preg_match()trả về luôn1
  • Mảng kết quả của các chuỗi con phù hợp: Nếu hoàn toàn không tìm thấy một chuỗi con ( (b)in ...a(b)?), thì mục tương ứng trong ereg()kết quả sẽ là FALSE, trong khi preg_match()đó nó sẽ không được đặt.

Nếu người ta không đủ dũng cảm để chuyển đổi của mình ereg()để preg_match(), người đó có thể sử dụng mb_ereg () , mà vẫn còn có sẵn trong PHP 7.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.