F# 对空格敏感的FParsec
我正在尝试使用FParsec实现一个对空格敏感的解析器,我将从定义一个函数开始,该函数将解析以F# 对空格敏感的FParsec,f#,fparsec,F#,Fparsec,我正在尝试使用FParsec实现一个对空格敏感的解析器,我将从定义一个函数开始,该函数将解析以nchars空格开头的文本行 以下是我目前掌握的情况: let test: Parser<string list,int> = let manyNSatisfy i p = manyMinMaxSatisfy i i p let p = fun (stream:CharStream<int>) -> let state = stream.UserS
n
chars空格开头的文本行
以下是我目前掌握的情况:
let test: Parser<string list,int>
= let manyNSatisfy i p = manyMinMaxSatisfy i i p
let p = fun (stream:CharStream<int>) ->
let state = stream.UserState
// Should fail softly if `state` chars wasn't parsed
let result = attempt <| manyNSatisfy state (System.Char.IsWhiteSpace) <| stream
if result.Status <> Ok
then result
else restOfLine false <| stream
sepBy p newline
let测试:解析器
=让many满足i p=many满足i p
让p=fun(流:CharStream)->
let state=stream.UserState
//如果未解析'state'字符,则应轻轻失败
让结果=尝试哦,天哪,多尴尬啊
我想要的是sepEndBy
,也就是说我应该终止对分隔符的解析。这看起来更为惯用。我已经硬编码了1
,但很容易提取为参数
let skipManyNSatisfy i = skipManyMinMaxSatisfy i i
let pMyText =
( // 1st rule
skipManyNSatisfy 1 System.Char.IsWhiteSpace // skip an arbitrary # of WhiteSpaces
>>. restOfLine false |>> Some // return the rest as Option
)
<|> // If the 1st rule failed...
( // 2nd rule
skipRestOfLine false // skip till the end of the line
>>. preturn None // no result
)
|> sepBy <| newline // Wrap both rules, separated by newLine
|>> Seq.choose id // Out of received string option seq, select only Some()
让skipmanynassistify i=skipmanyminmax满足i
让pMyText=
(//第1条规则
skipManyNSatisfy 1 System.Char.IsWhiteSpace//跳过任意的#个空格
>>.restOfLine false |>>Some//将其余部分作为选项返回
)
//如果第一条规则失败。。。
(//第二条规则
SkipPrestofLine false//跳到行尾
>>.preturn无//无结果
)
|>sepBy>Seq.choose id//Out-of-received string选项Seq,仅选择一些()
谢谢,尽管这确实极大地改变了我所做工作的语义。我不想/不需要跳过行。低级别实现的原因是获取该状态变量。@Khanzor好吧,如果您的主要目标是为类似于F#syntax的东西创建一个解析器,那么您可能需要计算空格数,然后将其传递给语法检查器以完成剩余的工作,正确吗?此wiki页面包含两个FParsec解析器实现,用于简单语法,其中包含大量空格: