2013-07-10 6 views
6

Tôi đang sử dụng regex với PowerGrep để tìm kiếm thông qua một loạt tệp. Tôi đang làm việc với các tệp java và mục tiêu của tôi là tìm tất cả bắt giữ blocks không chứa từ log trong khối để tôi có thể thêm ghi nhật ký. Có rất nhiều tập tin, do đó, đi qua chúng bằng tay là không thực sự khả thi.Regex tìm khối catch mà không cần đăng nhập

Các ví dụ về những gì nên được tìm thấy

catch (Exception e) { 
    //comment# 
    int math = 1 +2 * (3); 
    String email = "[email protected]"; 
    anothermethod.call(); 
    //no logging 
} 

catch(AnotherException e) {} //no logging 

Các ví dụ về những gì nên KHÔNG được tìm thấy

catch(AnotherException e) { 
    //some code 
    log.error("Error message"); 
    //some more code 
} 

catch(BadE_xception e) { log.error(e); }  

Tôi không phải là rất có kinh nghiệm với regex, nhưng đây là những gì tôi có cho đến nay:

đầu khối catch: catch\s*\(\s*\w*\s+\w*\s*\)\s*\{.*?

nhưng sau đó tôi không chắc chắn nơi để đi từ đó đến chỉ định không chứa log. Nếu bạn có ý tưởng về cách làm điều này mà không có regex, điều đó cũng hoàn hảo cho tôi. Cảm ơn

+0

Có thể có thể có các dấu ngoặc lồng nhau trong khối 'catch', phải không? Công cụ regex của PowerGREP không thể xử lý đệ quy (chưa). –

+0

Vâng, có những trường hợp đó. Kể từ khi đăng nhập là không hoàn toàn cần thiết, tôi sẵn sàng bỏ qua những người ngay bây giờ và chỉ nhận được các trường hợp không lồng nhau. – jlars62

Trả lời

8

Bạn có thể nhận được mức độ hữu hạn của các trường hợp lồng nhau, ít nhất.

Đối với trường hợp không có lồng, sửa đổi cuối biểu hiện của bạn:

catch\s*\(\s*\w*\s+\w*\s*\)\s*\{(?:[^}](?!\blog\b))*\} 
           ^^^^^^^^^^^^^^^^^^^^^^ 

Hãy phá vỡ này xuống.

  1. Chúng tôi đang xem xét các ký tự không }; do đó [^}]. Khi chúng tôi tìm thấy } đầu tiên, chúng tôi đã hoàn tất.
  2. (?!foo) được gọi là xác nhận tra cứu âm. Điều này có nghĩa là "Điểm này là không phải là, tiếp theo là foo".
  3. \b là từ giới hạn. Xung quanh log trong \b s đảm bảo rằng chúng tôi không nắm bắt được "các mặt tích cực sai" như "làm tắc nghẽn" và "hợp lý". Bạn muốn từ duy nhất, "đăng nhập".
  4. (?:foo) là một cách để nhóm một biểu thức mà không cần chụp. Đây không phải là quan trọng — bây giờ giả vờ nó giống như (foo). Mục đích của nó là để toàn bộ nhóm có thể được định lượng bởi *.
  5. Đưa nó tất cả cùng nhau: chúng tôi đang kiểm tra từng ký tự, mỗi một không là một }, và mỗi một không bị theo dõi bởi toàn bộ văn bản, log.

Điều đó đảm bảo rằng từ log không nằm trong khối catch không lồng nhau.

Bây giờ, hãy chuyển sang các trường hợp lồng nhau. Như @TimPietzcker đã chỉ ra, PowerGREP không hỗ trợ các biểu thức đệ quy, nhưng với mục đích của bạn, bạn có thể hài lòng với số lượng tổ hợphữu hạn. Dưới đây là những biểu hiện cho mức một của tổ:

catch\s*\(\s*\w*\s+\w*\s*\)\s*\{(?:[^{}](?!\blog\b)|\{(?:[^}](?!\blog\b))*\})*\} 
            ^   ^======================== 

Chúng tôi đã thêm nhân vật { đến lớp của các nhân vật chúng ta không thích. Điều này là bởi vì nếu chúng ta gặp phải ký tự này, chúng ta muốn chuyển đổi qua thay đổi (|) thành trường hợp lồng nhau, như bạn có thể thấy bằng cách so sánh phần được gạch chân bằng các dấu hiệu =, là bản sao chính xác của biểu thức "bên trong" gốc . Bạn có thể tiếp tục làm tổ theo cách này nhiều như bạn muốn, để nắm bắt một số lượng tùy ý các tổ hợp cân bằng.


Đây là mẫu cho 10 cấp độ lồng nhau, đủ cho hầu hết các ứng dụng thuộc loại này.

catch\s*\(\s*\w*\s+\w*\s*\)\s*\{(?:SEED|\{(?:SEED|\{(?:SEED|\{(?:SEED|\{(?:SEED|\{(?:SEED|\{(?:SEED|\{(?:SEED|\{(?:SEED|\{(?:SEED|\{(?:SEED)*\})*\})*\})*\})*\})*\})*\})*\})*\})*\})*\} 

nơi hạt giống đệ quy, [^{}](?!\blog\b). Tôi đã viết nó theo cách này vì vậy nó dễ dàng hơn để loại bỏ hoặc thêm các cuộc tiếp tục như mong muốn. Mở rộng, phía trên trở thành:

catch\s*\(\s*\w*\s+\w*\s*\)\s*\{(?:[^{}](?!\blog\b)|\{(?:[^{}](?!\blog\b)|\{(?:[^{}](?!\blog\b)|\{(?:[^{}](?!\blog\b)|\{(?:[^{}](?!\blog\b)|\{(?:[^{}](?!\blog\b)|\{(?:[^{}](?!\blog\b)|\{(?:[^{}](?!\blog\b)|\{(?:[^{}](?!\blog\b)|\{(?:[^{}](?!\blog\b)|\{(?:[^{}](?!\blog\b))*\})*\})*\})*\})*\})*\})*\})*\})*\})*\})*\} 
+0

Đẹp! Cảm ơn bạn rất nhiều vì câu trả lời và giải thích. – jlars62

+1

Không sao cả. Cũng được chỉnh sửa trong một biểu thức cho 10 cấp độ lồng nhau, để thuận tiện cho người xem trong tương lai. –