問題タブ [megaparsec]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票する
1 に答える
439 参照

parsing - foldLine で多くのブロックを解析する

この単純化された問題について、次のような入力を解析しようとしています

の中へ

私が試したコードは次のとおりです。

これは の 1 つのブロックに対して機能しitemsます。

しかし、解析しようとするとすぐにmany items、インデントされていない最初の行で失敗します。

または、さらに単純な入力で:

0 投票する
1 に答える
270 参照

parsing - 式ツリーのインデントを意識した解析

この質問へのフォローアップとして、変数と式を持つ式言語を解析しようとしていますcase ... of ...。構文はインデントベースにする必要があります。

  • すべての行が最初の行に対してインデントされている限り、式は複数の行にまたがることができます。つまり、これは単一のアプリケーションとして解析する必要があります。

    /li>
  • 式の各選択肢は、キーワードcaseに対してインデントされた独自の行にある必要があります。case右側は複数の行にまたがることができます。

    右辺としてと をcase使用して、2 つの選択肢を持つ単一に解析する必要があります。xf x y

コードを次のように簡略化しました。

ご覧のとおり、この回答の手法を使用して、キーワードよりもインデントされたエースでaltエルナティブを分離しようとしています。sp'case

問題

これは、アプリケーションのみで構成される単一の式で機能するようです。

リンクされた回答の手法を使用したそのような式のリストでは機能しません:

case行の折りたたみを使用しようとすると、式がゲートから失敗します。

case最も外側の式では行を折りたたむことなく、1 つの選択肢のみで機能します。

しかし、複数のエルナティブcaseがあるとすぐに失敗します:alt

私は何を間違っていますか?

0 投票する
1 に答える
79 参照

parsing - すべてのオプションを強制的にバックトラックすることは可能ですか?

関数宣言のためにこの構文を解析する必要があります

私はこのパーサーを書きました

解析できるが解析foo (x) = 1できないfoo x = 1

このコードを次のように解析しようとしてFunc "foo" (Label "x" 1)失敗することを理解しています。しかし、失敗した後、なぜそれを解析しようとできないのかFunc "foo" (Ident "x") = 1

それを行う方法はありますか?

また、私は交換しようとしましidentparamLabel

この場合、解析できますfoo x = 1が解析できませんfoo (x = 1) = 2

0 投票する
0 に答える
243 参照

haskell - Megaparsec: 解析中のマクロ展開

小さな DSL では、#defineC プリプロセッサ ディレクティブと同様に、マクロ定義を解析しています (ここでは単純な例を示します)。

パーサーが次の呼び出しに遭遇したとき

に展開されます

私の現在のアプローチは次のとおりです。

  • パーサーを State モナドでラップする
  • マクロ定義を解析するとき、それらの本体を未解析の状態で保存します(文字列として解析します)。
  • マクロ呼び出しを解析するときは、状態で定義を見つけ、本文の引数を置き換え、呼び出しをこの本文に置き換えて、解析を再開します。

最後のステップのコード:

このアプローチはきちんと仕事をします。ただし、いくつかの欠点があります。

複数回の解析

任意の有効な DSL 式をマクロ呼び出しの引数にすることができます。したがって、テキスト表現のみが必要ですが (マクロ本体で置き換える必要があります)、それらを解析してから再度文字列に変換する必要があります。次のカンマを探すだけではうまくいきません。次に、カスタマイズされた完全なマクロが解析されます。したがって、実際には、マクロ引数は 2 回解析されます (また、コストがかかる show-ed も行われます)。さらに、呼び出しごとに、(ほぼ同じ) 本体の新しい解析が必要になります。本文をメモリ内で解析しないでおく理由は、最大の柔軟性を可能にするためです。本文では、マクロ引数から DSL キーワードを構築することもできます。

エラー処理

展開された本文は未使用の入力の前に挿入される (呼び出しを置き換える) ため、最初と最後の入力はまったく異なる場合があります。解析エラーが発生した場合、展開されたエラーが発生した位置入力が可能です。ただし、エラーを処理するときは、拡張されていない元の入力しかありません。したがって、エラーの位置は一致しません。そのため、上記のコード スニペットでは、状態を使用して展開された入力を保存し、パーサーがエラーで終了したときに使用できるようにしています。これはうまく機能しますが、展開のたびに新しいテキスト配列 (入力ストリームはテキスト) がストリーム全体に割り当てられるため、非常にコストがかかることに気付きました。おそらく、展開された入力をテキストではなく文字列として保持する方が、この場合、つまり中間部分を置き換える必要がある場合に安くなるでしょうか?

この質問の理由は次のとおりです。

  • 上記の2つの問題に関する提案/コメントをいただければ幸いです
  • 誰もがより良いアプローチを提案できますか?
0 投票する
1 に答える
133 参照

haskell - megaparsec を使用した異なる位置の複数のエラー

大学のプロジェクトでプログラミング言語を解析するために megaparsec を使用します。しかし、複数のエラーを報告する方法を探しました。

私は withRecovery について知っていて、この問題を見ましたが、異なる位置でエラーが発生するケースについては知りませんでした。

たとえば、このJavaコードでは:

error1 「行 3 列 10 に期待される型」と error2 「行 5 列 22 にセミコロンがありません」があります。

エラーメッセージを組み合わせることができることは知っていますfailureが、複数の位置についてはどうですか? それ、どうやったら出来るの ?

0 投票する
1 に答える
543 参照

haskell - 開始と終了の記号を使用して Megaparsec でブロック コメントを解析する

Megaparsec を使用して、Haskell でこれに似たテキストを解析したいと考えています。

ここで、# START SKIP# END SKIPは、解析するテキスト ブロックの開始と終了を示します。

skipBlockCommentと比較して、パーサーが開始マーカーと終了マーカーの間の行を返すようにします。

これは私のパーサーです。

skipパーサーは意図したとおりに機能します。

たとえば、開始マーカーと終了マーカー内に可変量の空白を許可するために# START SKIP、次のことを試しました。

を使用skip'して上記のテキストを解析すると、次のエラーが発生します。

このエラーの原因と修正方法を知りたいです。