我正在学习如何使用名为Alex 1 的Haskell词法分析器工具。
我正在尝试为此字符串实现词法分析器(电子邮件“From:”标题):
From: "John Doe" <john@doe.org>
我想把它分解成这个令牌列表:
[
From,
DisplayName "John Doe",
Email,
LocalName "john",
Domain "doe.org"
]
以下是我的实施。如果字符串不包含显示名称,它可以正常工作。也就是说,这很好用:
let s = "From: <john@doe.org>"
alexScanTokens s
但是,当我包含显示名称时,我收到以下错误消息:
[From*** Exception: lexical error
也就是说,这会导致错误:
let s = "From: \"John Doe\" <john@doe.org>"
alexScanTokens s
我猜我的Alex
程序的这一部分导致错误:
\"[a-zA-Z ]+\" { \s -> DisplayName (init (tail s)) }
在Alex
中,左侧是正则表达式:
\"[a-zA-Z ]+\"
,右侧是找到与正则表达式匹配的字符串时要采取的操作:
{ \s -> DisplayName (init (tail s)) }
关于问题可能是什么的任何想法?
{
module Main (main) where
}
%wrapper "basic"
$digit = 0-9 -- digits
$alpha = [a-zA-Z] -- alphabetic characters
tokens :-
$white+ ;
From: { \s -> From }
\"[a-zA-Z ]+\" { \s -> DisplayName (init (tail s)) }
\< { \s -> Email }
[$alpha]+@ { \s -> LocalPart (init s) }
[$alpha\.]+> { \s -> Domain (init s) }
{
-- Each action has type :: String -> Token
-- The token type:
data Token =
From |
DisplayName String |
Email |
LocalPart String |
Domain String
deriving (Eq,Show)
main = do
s <- getContents
print (alexScanTokens s)
}
1 可以在以下网址找到“Alex”词法分析工具:http://www.haskell.org/alex/doc/html/introduction.html
答案 0 :(得分:7)
这是"John Doe"
中造成麻烦的空间。
Whitespace is ignored in character sets,如[a-zA-Z ]
。要包含空格,您需要使用反斜杠来逃避它,例如: [a-zA-Z\ ]
。
另外,我不禁注意到词法分析器可能是这项工作的错误工具。考虑使用例如编写适当的解析器Parsec 子>