如何在Haskell中使用正则表达式提取字符串?
let x = "xyz abc" =~ "(\\w+) \\w+" :: String
这不是事件得到匹配
let x = "xyz abc" =~ "(.*) .*" :: String
但是x会以“xyz abc”结尾,如何只提取第一个正则表达式组,使x为“xyz”?
答案 0 :(得分:18)
我编写/维护了regex-base,regex-pcre和regex-tdfa这样的包。
在regex-base中,Text.Regex.Base.Context模块记录了=〜使用的大量RegexContext实例。这些是在RegexLike之上实现的,它提供了调用matchText和matchAllText的基本方法。
KennyTM提到的[[String]]是RegexContext的另一个实例,可能是也可能不是最适合你的实例。一个综合实例是
RegexContext a b (AllTextMatches (Array Int) (MatchText b))
type MatchText source = Array Int (source, (MatchOffset, MatchLength))
可用于获取所有内容的MatchText:
let x :: Array Int (MatchText String)
x = getAllTextMatches $ "xyz abc" =~ "(\\w+) \\w+"
此时x是组匹配的Array Int匹配的Array Int。
请注意,“\ w”是Perl语法,因此您需要使用regex-pcre来访问它。如果你想要Unix / Posix扩展的正则表达式,你应该使用跨平台的regex-tdfa,并避免使用regex-posix来实现regex.h库中每个平台的错误。
请注意,Perl vs Posix不仅仅是“\ w”这样的语法问题。他们使用非常不同的算法,并经常返回不同的结果此外,时间和空间的复杂性也非常不同。对于长度为'n'的字符串匹配,Perl样式(regex-pcre)的时间可以是O(exp(n)),而使用regex-posix的Posix样式在时间上总是O(n)。
答案 1 :(得分:14)
将结果转换为[[String]]
。然后,您将获得匹配列表,每个匹配文本和捕获的子组列表。
Prelude Text.Regex.PCRE> "xyz abc more text" =~ "(\\w+) \\w+" :: [[String]]
[["xyz abc","xyz"],["more text","more"]]