2009-03-09 36 views
12

Tôi muốn nhận được chỉ là tên tập tin sử dụng regex, vì vậy tôi đã cố gắng mọi thứ đơn giản nhưRegex: Nhận tên tệp không có phần mở rộng trong một lần chụp?

([^\.]*) 

mà công việc dĩ nhiên chỉ khi tên tập tin có một phần mở rộng. Nhưng nếu nó là adfadsfads.blah.txt Tôi chỉ muốn adfadsfads.blah. Làm thế nào tôi có thể làm điều này với regex?

Về câu hỏi của David, 'tại sao bạn sẽ sử dụng regex' cho câu hỏi này, câu trả lời là, 'để giải trí'. Thực tế, mã tôi đang sử dụng đơn giản là

length_of_ext = File.extname(filename).length 
filename = filename[0,(filename.length-length_of_ext)] 

nhưng tôi muốn tìm hiểu regex bất cứ khi nào có thể vì nó luôn xuất hiện tại các bữa tiệc cocktail Geek.

+0

Daniel, trong trường hợp này, tôi khuyên bạn nên mua một công cụ như RegexBuddy. Sẽ thú vị hơn khi chơi với regex nếu bạn có một công cụ như thế. Bạn thậm chí có thể gỡ lỗi các biểu thức chính quy trong một công cụ như vậy. Một thực sự khuyên bạn nên. –

+0

Cảm ơn David. Tôi sử dụng Regex Coach, điều này thực sự độc đáo. –

Trả lời

33

Hãy thử điều này:

(.+?)(\.[^.]*$|$) 

Điều này sẽ:

  • Capture tên tập tin bắt đầu bằng một dấu chấm (ví dụ: ".logs" là một file có tên ".logs", không phải là một tập tin mở rộng), mà là phổ biến trong Unix.
  • Nhận mọi thứ trừ dấu chấm cuối cùng: "foo.bar.jpeg" đưa bạn "foo.bar".
  • Xử lý tệp không có dấu chấm: "chữ cái bí mật" sẽ đưa bạn "thư bí mật".

Lưu ý: như commenter j_random_hacker gợi ý, điều này thực hiện như quảng cáo, nhưng bạn có thể muốn đi trước mọi thứ với một neo cho các mục đích dễ đọc.

+1

Có một lời giải thích tốt về điều này tại http://www.movingtofreedom.org/2008/04/01/regex-match-filename-base-and-extension/ – bernie

+0

Ngôi sao phải là một điểm cộng, tôi nghĩ - mặc dù không rõ một tệp được gọi là 'nhật ký'. nên quay trở lại. –

+1

Mặc dù điều này không hoạt động như được quảng cáo, tôi có thể đề xuất thêm một ký tự "^" cho mục đích dễ đọc không? Nếu không có neo, một lập trình viên nhìn thấy regex này lần đầu tiên cần thực hiện một phân tích chi tiết để xác minh rằng trận đấu trả về luôn bắt đầu ở đầu chuỗi. –

4

Tất cả những gì theo sau là một dấu chấm theo sau là một hoặc nhiều ký tự đó không phải là một dấu chấm, tiếp theo là chuỗi end-of-:

(.+?)\.[^\.]+$ 

Các mọi thứ-trước-the-qua-dot được nhóm để dễ dàng thu hồi.

Nếu bạn không chắc chắn 100% mỗi file sẽ có phần mở rộng, hãy thử:

(.+?)(\.[^\.]+$|$) 
+0

Nó không khớp với tên tệp không có phần mở rộng –

3

cách khoảng 2 chụp một cho cuối cùng và một cho tên tập tin.

ví dụ:

(.+?)(?:\.[^\.]*$|$) 
+0

Đó là tất cả, nhưng vì tôi sẽ loại bỏ tên tệp, tại sao lại bận tâm? Tôi muốn một regex chỉ nhận được tên tập tin. –

+0

Điều này cũng sẽ không khớp với tên tệp không chứa phần mở rộng. –

0

Ok, tôi không chắc chắn lý do tại sao tôi sẽ sử dụng cụm từ thông dụng cho điều này. Nếu tôi biết ví dụ rằng chuỗi là một filepath đầy đủ, sau đó tôi sẽ sử dụng một API để có được tên tập tin. Cụm từ thông dụng rất mạnh mẽ nhưng đồng thời khá phức tạp (bạn vừa chứng minh rằng bằng cách hỏi làm thế nào để tạo ra một regex đơn giản như vậy). Ai đó nói: bạn đã có một vấn đề mà bạn quyết định giải quyết nó bằng cách sử dụng các biểu thức thông thường. Bây giờ bạn có hai vấn đề.

Hãy suy nghĩ lại. Nếu bạn đang ở trên nền tảng .NET chẳng hạn, hãy xem System.IO.Path lớp.

+0

Vâng, điều đó không vui lắm, phải không? Dù sao, điều chỉnh câu hỏi cho câu trả lời của bạn, xin vui lòng xem ở trên. Cảm ơn. –

0
^(.*)\\(.*)(\..*)$ 
  1. Gets con đường mà không có cuối cùng \
  2. Các tập tin mà không cần mở rộng
  3. Các phần mở rộng với một .

Ví dụ:

c:\1\2\3\Books.accdb
(c:\1\2\3)(Books)(.accdb)

Không hỗ trợ nhiều . trong tên tập tin có hỗ trợ . trong đường dẫn tập tin

0

tôi đã sử dụng mô hình này để tìm kiếm đơn giản:

^\s*[^\.\W]+$ 

cho văn bản này:

file.ext 
    fileext 

    file.ext.ext 
file.ext 
fileext 

Nó tìm thấy fileext trong dòng thứ hai và cuối cùng.
Tôi đã áp dụng nó trong chế độ xem dạng cây văn bản của một thư mục (có dấu cách như là thụt lề).

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