0

FParsec を使用して、標準入力ストリームから正常に解析できないようです。私は自分のケースをこの非常に単純なコードに減らしました:

match (runParserOnStream (pstring "test" .>> FParsec.CharParsers.newline) () "stdin" (Console.OpenStandardInput ()) Console.InputEncoding) with
    | Success(result, _, _)   -> printfn "Success: %A" result
    | Failure(errorMsg, perr, _) -> printfn "Failure: %s" errorMsg

しかし、プログラムを実行し、文字列テストを入力してEnterキーを押すと、そこでハングし、理由がわかりません..

解決策は何ですか?

4

2 に答える 2

6

パフォーマンス上の理由と単純さのために、FParsec は入力ストリームをブロックごとに読み取ります (または、解析を開始する前に完全なストリームを文字列に読み取ります)。詳細については、たとえば、この回答を参照してください: Chunked Parsing with FParsec

FParsec を使用して REPL からの入力を解析する場合は、入力ストリーム内のターミネータ (たとえば、FSI コンソールのように ";;" の後に改行が続く) を待機する単純なスキャナを実装できます。このようなターミネータに遭遇すると、ターミネータまでの入力を文字列にコピーし、評価のために FParsec パーサーに渡します。

于 2012-10-11T23:09:10.910 に答える
2

FParsec のソース コードが利用できるので、それをステップ実行して、バッファがいっぱいになるか、ストリームの終わりが通知されるまで、入力ストリームを読み取ることを確認するのは簡単でした。

または、一度に 1 行ずつ読み取ることもできます。

let rec parseConsoleInput() =
  let parser = pstring "text" .>> eof
  Console.Write("> ")
  match Console.ReadLine() with
  | null | "" -> ()
  | input -> 
    match run parser input with
    | Success(result, _, _) -> printfn "Success: %A" result
    | Failure(msg, _, _) -> printfn "Failure: %s" msg
    parseConsoleInput()
于 2012-10-11T19:16:42.803 に答える