2009-02-13 20 views

Trả lời

26

này nghe có vẻ như một công việc cho lookbehinds, mặc dù bạn nên biết rằng không phải tất cả các hương vị regex hỗ trợ họ. Trong ví dụ của bạn:

(?<=\bipsum\s)(\w+) 

này sẽ phù hợp bất kỳ chuỗi thư nhân vật mà sau "ông" như toàn bộ một từ theo sau bởi một dấu cách. nó không phù hợp với "rất" riêng của mình, bạn không cần phải lo lắng về reinserting nó trong trường hợp ví dụ thay thế.

Như 1 cho biết, tuy nhiên, một số hương vị (JavaScript, ví dụ) không hỗ trợ lookbehind ở tất cả. Nhiều người khác (nhất, trên thực tế) chỉ hỗ trợ "width cố định" lookbehinds - vì vậy bạn có thể sử dụng ví dụ này nhưng không phải bất kỳ toán tử lặp lại. (Nói cách khác,(?<=\b\w+\s+)(\w+)sẽ không hoạt động.)

+0

đánh bại tôi quá :) – annakata

+0

Lookbehinds có xu hướng khá hạn chế khi nói đến việc sử dụng ký tự đại diện mặc dù. – cletus

+0

Có thể thậm chí không cần thiết ở đây. Tùy thuộc vào những gì 'tôi muốn phù hợp' trong câu hỏi đề cập đến, xem giải pháp của David Kemp. – user55400

-1

rằng \ b \ B

EDIT (. *): mặc dù phụ thuộc vào thực hiện regex của bạn, điều này có thể bị đói và tìm tất cả các từ sau đó

+0

Điều đó sẽ phù hợp với phần còn lại của câu. – cletus

+0

bạn phải làm cho rằng không phù hợp – tliff

+0

Trên thực tế nó không thực hiện phụ thuộc, hoặc ít nhất tôi đã không bao giờ đi qua một thực hiện regex đó là không tham lam theo mặc định. Không tham lam luôn là một công tắc (ít nhất là trong Perl, PHP, Java và .Net). – cletus

1

rằng \ b (\ w *)

+0

Điều đó dường như chỉ khớp với ipsum. –

+0

Tôi có thể làm cho \ b + (\ w +) ít nhất – cletus

+0

ipsum \ b + (\ w +) không phải là regex hợp lệ. –

4

Một số phản ứng khác đã đề nghị sử dụng một regex mà không phụ thuộc vào lookbehinds, nhưng 1 suy nghĩ hoàn toàn, ví dụ làm việc là cần thiết để có được điểm qua. Ý tưởng là bạn phù hợp với toàn bộ chuỗi ("Nghiên cứu" cộng với chữ tiếp theo) theo cách thông thường, sau đó sử dụng một nhóm chụp để cô lập các phần mà bạn quan tâm. Ví dụ,

String s = "Lorem ipsum dolor sit amet, consectetur " + 
    "adipiscing elit. Nunc eu tellus vel nunc pretium " + 
    "lacinia. Proin sed lorem. Cras sed ipsum. Nunc " + 
    "a libero quis risus sollicitudin imperdiet."; 

Pattern p = Pattern.compile("ipsum\\W+(\\w+)"); 
Matcher m = p.matcher(s); 
while (m.find()) 
{ 
    System.out.println(m.group(1)); 
} 

Lưu ý rằng điều này sẽ in cả "thông minh" và "bây giờ". Để làm điều đó với phiên bản lookbehind, bạn sẽ phải làm một cái gì đó giống như hackish:

Pattern p = Pattern.compile("(?<=ipsum\\W{1,2})(\\w+)"); 

Đó là Java, mà đòi hỏi sự lookbehind có chiều dài tối đa hiển nhiên. Một số hương vị không có thậm chí là nhiều tính linh hoạt, và dĩ nhiên, một số không hỗ trợ lookbehinds ở tất cả.

Tuy nhiên, vấn đề người lớn dường như có trong các ví dụ của họ không phải là với lookbehinds, nhưng với ranh giới từ. Cả David Kemp và CK dường như mong đợi \b để phù hợp với nhân vật không gian sau khi 'M', nhưng nó không; nó phù hợp với vị trí (hoặc ranh giới) giữa 'm' và không gian.

Đó là một sai lầm phổ biến, một 1've thậm chí nhìn thấy lần lặp đi lặp lại trong một vài cuốn sách và hướng dẫn, nhưng xây dựng từ biên giới, \b không bao giờ phù hợp với bất kỳ ký tự. Đó là một sự khẳng định zero-byte, như lookarounds và neo (^, $, \z, vv), và những gì nó phù hợp là một vị trí mà một trong hai là trước bởi một nhân vật từ và không theo sau là một, hoặc theo sau là một nhân vật từ và không đi trước một.

0

Với javascript bạn có thể sử dụng (?=ipsum.*?(\w+))

này sẽ nhận được sự xuất hiện thứ hai cũng như (Nunc)

Các vấn đề liên quan