2011-10-24 29 views
17

Tôi đã tìm kiếm một số tài liệu hoặc hướng dẫn về biểu thức chính quy của Haskell cho các độ tuổi. Không có thông tin hữu ích nào trên số HaskellWiki page. Nó chỉ đơn giản đưa ra thông điệp khó hiểu:PCRE trong Haskell - cái gì, ở đâu, như thế nào?

Documentation 
Coming soonish. 

Có một ngắn gọn blog post mà tôi đã tìm thấy khá hữu ích, tuy nhiên nó chỉ thoả thuận với Posix biểu thức thông thường, không PCRE.

Tôi đã làm việc với Posix regex trong một vài tuần và tôi đi đến kết luận rằng đối với nhiệm vụ của mình, tôi cần PCRE.

Vấn đề của tôi là tôi không biết bắt đầu từ đâu với PCRE trong Haskell. Tôi đã tải xuống regex-pcre-builtin với cabal nhưng tôi cần một ví dụ của một chương trình kết hợp đơn giản để giúp tôi bắt đầu.

  • Có thể thực hiện đối sánh nhiều dòng không?
  • Tôi có thể lấy lại các kết quả theo định dạng sau: [(MatchOffset,MatchLength)] không?
  • Tôi có thể lấy lại các định dạng khác trong các định dạng nào khác?

Cảm ơn bạn rất nhiều vì đã giúp đỡ!

Trả lời

5

Vâng, tôi đã viết nhiều trang wiki và có thể đã viết "Sắp ra mắt". Gói regex-pcre là gói PCRE của tôi sử dụng giao diện regex-base, nơi regex-base được sử dụng làm giao diện cho một số phụ trợ động cơ biểu thức chính quy rất khác nhau. Gói gọn nhẹ của Don Stewart không có lớp trừu tượng này và do đó nhỏ hơn nhiều.

Bài đăng trên blog trên Text.Regex.Posix sử dụng gói regex-posix của tôi cũng nằm trên cơ sở regex-base. Do đó, việc sử dụng regex-pcre sẽ rất giống với bài đăng trên blog đó, ngoại trừ việc biên dịch các tùy chọn thực thi của PCRE khác nhau là &.

Để định cấu hình regex-pcre, Text.Regex.PCRE.Wrap module có các hằng số bạn cần. Sử dụng makeRegexOptsM từ regex-base để chỉ định các tùy chọn.

10

Có hai lựa chọn chính khi muốn sử dụng regexes PCRE kiểu trong Haskell:

  • regex-pcre sử dụng giao diện tương tự như mô tả ở chỗ bài đăng blog (và cũng có trong RWH, như tôi nghĩ một phiên bản mở rộng của bài đăng trên blog đó); điều này có thể được mở rộng tùy chọn với pcre-less. regex-pcre-builtin dường như là ảnh chụp nhanh trước khi phát hành và có thể không được sử dụng.

  • pcre-light là các ràng buộc với thư viện PCRE. Nó không cung cấp các kiểu trả về bạn đang sử dụng, chỉ là tất cả các kết quả phù hợp (nếu có). Tuy nhiên, gói pcre-light-extras cung cấp lớp học MatchResult, mà bạn có thể cung cấp ví dụ như vậy. Điều này có thể được tăng cường bằng cách sử dụng regexqq cho phép bạn sử dụng dấu ngoặc kép để đảm bảo rằng kiểm tra kiểu mẫu regex của bạn; tuy nhiên, nó không hoạt động với GHC-7 (và trừ khi ai đó tiếp tục duy trì nó, nó sẽ không).

Vì vậy, giả định rằng bạn đi với regex-pcre:

  • Theo this câu trả lời, vâng.

  • Tôi nghĩ vậy, thông qua loại MatchArray (nó trả về một mảng, sau đó bạn có thể lấy danh sách ra khỏi).

  • Xem here cho tất cả các kết quả có thể có từ regex.

+0

Tôi nhận được lỗi 'Không nằm trong phạm vi' compNewLine'' khi tôi thử phương pháp đó cho kết hợp nhiều dòng. Tôi nghĩ nó chỉ hoạt động cho Posix. –

+0

@NickBrunt [compMultiline] (http://hackage.haskell.org/packages/archive/regex-pcre/0.94.2/doc/html/Text-Regex-PCRE-Wrap.html#v:compMultiline) có thể sau đó? – ivanm

+0

Không phải là tính năng bổ sung nhẹ nhàng của máy tính? – mcandre

5

regexpr là một PCRE-ish lib khác là nền tảng và nhanh chóng bắt đầu.

9

Ngoài ra còn có regex-applicative mà tôi đã viết.

Ý tưởng là bạn có thể gán một số ý nghĩa cho mỗi phần của cụm từ thông dụng và sau đó soạn chúng, giống như khi bạn viết các trình phân tích cú pháp bằng Parsec.

Đây là một ví dụ - phân tích cú pháp URL đơn giản.

import Text.Regex.Applicative 

data Protocol = HTTP | FTP deriving Show 

protocol :: RE Char Protocol 
protocol = HTTP <$ string "http" <|> FTP <$ string "ftp" 

type Host = String 
type Location = String 
data URL = URL Protocol Host Location deriving Show 

host :: RE Char Host 
host = many $ psym $ (/= '/') 

url :: RE Char URL 
url = URL <$> protocol <* string "://" <*> host <* sym '/' <*> many anySym 

main = print $ "http://stackoverflow.com/questions" =~ url 
+1

Oooohhh, trông đẹp quá! – ivanm

2

Tôi tìm thấy rex cũng khá đẹp, tích hợp ViewPatterns là một ý tưởng hay.

Mặc dù có thể tiết lộ chi tiết nhưng điều đó một phần gắn liền với khái niệm regex.

parseDate :: String -> LocalTime 
parseDate [rex|(?{read -> year}\d+)-(?{read -> month}\d+)- 
     (?{read -> day}\d+)\s(?{read -> hour}\d+):(?{read -> mins}\d+): 
     (?{read -> sec}\d+)|] = 
    LocalTime (fromGregorian year month day) (TimeOfDay hour mins sec) 
parseDate [email protected]_ = error $ "invalid date " ++ v 

Điều đó nói rằng tôi chỉ phát hiện regex-applicative đề cập trong một trong những câu trả lời khác và nó có thể là một lựa chọn tốt hơn, có thể ít tiết và nhiều thành ngữ, mặc dù rex có học tập đường cong cơ bản zero nếu bạn biết biểu thức thông thường có thể là một điểm cộng.

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