首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >导管和Attoparsec -提取分隔的文本

导管和Attoparsec -提取分隔的文本
EN

Stack Overflow用户
提问于 2015-05-23 01:44:32
回答 1查看 205关注 0票数 0

假设我有一个带有文本分隔符的文档,该文档由Jade样式括号分隔,如{{foo}}。我编写了一个Attoparsec解析器,它似乎正确地提取了foo

代码语言:javascript
复制
findFoos :: Parser [T.Text]
findFoos = many $ do
  manyTill anyChar (string "{{")
  manyTill letter (string "}}")

测试表明,它有效:

代码语言:javascript
复制
> parseOnly findFoos "{{foo}}"
Right ["foo"]
> parseOnly findFoos "{{foo}} "
Right ["foo"]

现在,使用Data.Conduit.Attoparsec模块在conduit-extra中,我似乎遇到了奇怪的行为:

代码语言:javascript
复制
> yield "{{foo}}" $= (mapOutput snd $ CA.conduitParser findFoos) $$ CL.mapM_ print
["foo"]
> yield "{{foo}} " $= (mapOutput snd $ CA.conduitParser findFoos) $$ CL.mapM_ print
-- floods stdout with empty lists

这就是你想要的行为吗?这里有我应该使用的管道实用工具吗?对此的任何帮助都将是巨大的!

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2015-05-23 08:19:20

因为它使用many,所以当findFoos找不到任何分隔的文本时,它将返回[]而不消耗输入。

另一方面,conduitParser在流上反复应用解析器,返回每个解析的值,直到它耗尽流为止。

"{{foo}} "的问题是解析器将消耗{{foo}},但是在流中空白仍未使用,因此解析器的进一步调用总是返回[]

如果您将findFoos重新定义为一次使用一个引用的元素,包括尾随空格,那么它应该可以工作:

代码语言:javascript
复制
findFoos' :: Parser String
findFoos' = do
   manyTill anyChar (string "{{")
   manyTill letter (string "}}") <* skipSpace

现实中的示例在括号内的文本之间将有其他字符,因此在每次解析后跳过“额外的内容”(而不消耗下一个解析的任何{{打开大括号)就会涉及到更多的问题。

也许下面这样的东西会起作用:

代码语言:javascript
复制
findFoos'' :: Parser String
findFoos'' = do
    manyTill anyChar (string "{{")
    manyTill letter (string "}}") <* skipMany everythingExceptOpeningBraces
  where 
    -- is there a simpler / more efficient way of doing this?
    everythingExceptOpeningBraces =
        -- skip one or more non-braces
        (skip (/='{') *> skipWhile (/='{'))
        <|> 
        -- skip single brace followed by non-brace character
        (skip (=='{') *> skip (/='{'))
        <|>
        -- skip a brace at the very end 
        (skip (=='{') *> endOfInput)

(但是,如果流中没有任何括号内的文本,则此解析器将失败。也许您可以构建一个Parser (Maybe Text),在这种情况下返回Nothing。)

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/30408059

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档