Đối với regex, cú pháp tìm kiếm cho đến khi nào nhưng không bao gồm là gì? Kinda như:
Haystack:
The quick red fox jumped over the lazy brown dog
Expression:
.*?quick -> and then everything until it hits the letter "z" but do not include z
Đối với regex, cú pháp tìm kiếm cho đến khi nào nhưng không bao gồm là gì? Kinda như:
Haystack:
The quick red fox jumped over the lazy brown dog
Expression:
.*?quick -> and then everything until it hits the letter "z" but do not include z
Câu trả lời:
Cách nói rõ ràng "tìm kiếm cho đến khi X
không bao gồm X
" là:
(?:(?!X).)*
đâu X
có thể là bất kỳ biểu thức chính quy nào.
Tuy nhiên, trong trường hợp của bạn, điều này có thể là quá mức cần thiết - đây là cách dễ nhất là
[^z]*
Điều này sẽ khớp với bất kỳ thứ gì ngoại trừ z
và do đó dừng ngay trước lần tiếp theo z
.
Như vậy .*?quick[^z]*
sẽ phù hợp The quick fox jumps over the la
.
Tuy nhiên, ngay sau khi bạn có nhiều hơn một chữ cái đơn giản để tìm kiếm (?:(?!X).)*
, chẳng hạn như
(?:(?!lazy).)*
- nối bất cứ thứ gì cho đến khi bắt đầu từ lazy
.
Điều này đang sử dụng một khẳng định nhìn trước , cụ thể hơn là một cái nhìn tiêu cực.
.*?quick(?:(?!lazy).)*
sẽ phù hợp The quick fox jumps over the
.
Giải trình:
(?: # Match the following but do not capture it:
(?!lazy) # (first assert that it's not possible to match "lazy" here
. # then match any character
)* # end of group, zero or more repetitions.
Hơn nữa, khi tìm kiếm từ khóa, bạn có thể muốn bao quanh chúng bằng các neo ranh giới từ: \bfox\b
sẽ chỉ khớp với từ hoàn chỉnh fox
nhưng không khớp với từ cáo trong foxy
.
Ghi chú
Nếu văn bản được đối sánh cũng có thể bao gồm dấu ngắt dòng, bạn sẽ cần đặt tùy chọn "chấm khớp với tất cả" của công cụ regex của mình. Thông thường, bạn có thể đạt được điều đó bằng cách sử dụng trước (?s)
regex, nhưng điều đó không hoạt động trong tất cả các công cụ regex (đặc biệt là JavaScript).
Giải pháp thay thế:
Trong nhiều trường hợp, bạn cũng có thể sử dụng một giải pháp đơn giản hơn, dễ đọc hơn đó là sử dụng bộ định lượng lười biếng. Bằng cách thêm a ?
vào bộ *
định lượng, nó sẽ cố gắng khớp càng ít ký tự càng tốt từ vị trí hiện tại:
.*?(?=(?:X)|$)
sẽ khớp với bất kỳ số ký tự nào, dừng ngay trước X
(có thể là bất kỳ regex nào) hoặc cuối chuỗi (nếu X
không khớp). Bạn cũng có thể cần đặt tùy chọn "chấm phù hợp với tất cả" để tùy chọn này hoạt động. (Lưu ý: Tôi đã thêm một nhóm không chụp xung quanh X
để cách ly đáng tin cậy với nhóm thay thế)
(?:...)
không chụp? Nó hoạt động với ((?!X).)*
?
grep
để lọc các yêu cầu chỉ cho một cơ sở dữ liệu từ mysql bin transformet trong sql. Đây là con thú:grep -Po "(?s)use database_to_keep(.*?)(?=^use)" mysql-bin.000045.sql > filtered.sql
Up
quan trọng, lệnh cuối cùng không phải là người tôi đã sử dụng:grep -Po "(?s)use database_to_keep(.*?)(?:(?!^use).)*" mysql-bin.000045.sql > filtered.sql
$
thay thế: thay thế .*?(?=X)
bằng.*?(?=X|$)
Một cú pháp regex lookahead có thể giúp bạn đạt được mục tiêu của bạn. Vì vậy, một regex cho ví dụ của bạn là
.*?quick.*?(?=z)
Và điều quan trọng là phải lưu ý .*?
kết hợp lười biếng trước tìm kiếm (?=z)
: biểu thức khớp với một chuỗi con cho đến khi xuất hiện đầu tiên của z
chữ cái.
Đây là mẫu mã C #:
const string text = "The quick red fox jumped over the lazy brown dogz";
string lazy = new Regex(".*?quick.*?(?=z)").Match(text).Value;
Console.WriteLine(lazy); // The quick red fox jumped over the la
string greedy = new Regex(".*?quick.*(?=z)").Match(text).Value;
Console.WriteLine(greedy); // The quick red fox jumped over the lazy brown dog
Thử cái này
(.*?quick.*?)z
grep
, nhưng câu trả lời này thì có.