BEHAVIOR"の"Left-recursion"も参照のこと。problem.Parse::RecDescentの文法で、サブ規則に関する質問があります。次のコードは、私の抱えている問題を浮き彫りにさせてくれる最良の事例です。各行の最初の0か1でもって、予想結果が通ったのか失敗したのかが示されます。this.ところが、期待に反して文法はarg1、arg1,arg2,の行を拒絶しません。サブ規則の終端要素のカンマはマッチして消費されています。やって直せばいいかわからず途方にくれています。pattern.これは文字列の一部にマッチしている。アンカーを置かない限り、これは正しい。最後には概して/\z/を使っている。withまた、あなたのカンマ区切りの文字列は、次のように単純に解析できる。manpage.これはP::RDのマニュアルにある例が示している通り。text:このテキストにマッチする。it."Bad"をプリントする*だろう*。PRDはマッチしなかったのだ。テキストを正しく受け入れる方法はないのか?と。例で、文法を軽く書き直してみよう(次のどちらかになる)。うまく解析するような追加の機能があるかどうか?ということだ。ようにできるのか?ということになる。doesn't.RecDescentパーサはそのような仕事をしない。後戻りしない;ただ失敗するだけだ。バックトラック機能も取り込むことを妨げるものは何も無い。RecDescentはそうしない。昔ながらの簡素な正規表現を使うことになる。details.が必要とするものだ。これは文字列とqr-クォート正規表現をとる。詳細はParse::RecDescentのドキュメントを見て欲しい。Separatorsの所も見てもらいたい。私の議論については以下を見ていただきたい。versions.RecDescentは完全グラフ遷移によるn個の左再帰のループの探査を行なう。初期バージョン以来、そのようにやてきた。しないように思えます。myruleは失敗するはずです。その失敗は問題にならないということだ。mysubruleが発見されれば、myruleはマッチすることができるから。それは確かにそうなっている。定石は、照合の最後に"アンカーを置く"ことだ。Grunaerによって指摘されたように、この答えは部分的に間違っている。なければこの規則は失敗する。well.このやり方は、複雑になりそうな否定先読みを指定しなくてすむ。この方法はサブ規則の幾つかのレベルを超えても動作する。though:現時点では、できない(しかしToDoリストに入っている)。problem.これで問題となっている実際に生成されたコードが示される。anywhere.再帰下降パーサでは独立した字句解析がありません。任意の場所にあるCコのメントを取り除くための方法はありますか。whitespace!もちろん。"\n".Parse::RecDescentを使って一行毎にパースしようとしています。行は"\n"で終わります。results.このケースのための文法を準備するのは単純明快なことです。次のプログラムは何ら結果を生み出しません。wrong?RecDescentは改行を認識しません。その後ろに別の数字が続く"。(メジャー及びマイナーバージョン)を取り出したい。(RecDescentがやらない先読み/バックトラックを得るために)。22"."カラム形式"が固定している行をパースしています。"一単語、いくつかの空白、それから22列目から始める別の一単語"です。this:うーむ、もっと簡単にできそうだ。word.これは最初の単語の後のどんな空白もスキップしないから。failure.これはうまいやり方で、より適切なように見えます。条件が失敗すると、必ずしもundefではない形で偽の値が発生します。それでこのケースでは、この条件を評価すると0を得ることになります。残念なことに、それは失敗へと導いてはくれません。これなら、間違いなくプロダクションは直ちに失敗になります。like:RecDescentの文法内で、私の言語にマクロをサポートしたいと思います。ために引数をサポートします。(x,y)はその式の中で置き換えられます。これは単純なことにみえます。ああ、私にはそうではないのです(所詮私はmush4brains[質問者のハンドル])。redundant.exprは文法内で完全に定義されています。それで...標準的なPerlの置換を使えばよいと考えました。これはうまくいかないようです。ある程度知識を必要としているからです。最初の文法は、二番目の文法全部を簡略化したものです。これもまた幾分冗長なように思えます。namespace00001)を持っているようです。出してこれらのパーサを複製しようとしました。パーサが同じ名前空間を共有してしまいます。そこのグローバル変数が他のパーサによって上書きされてしまいます。patch以下に必要となるパッチを示します。読むのかについて示している。つくるために文を解析する。新しい文をつくるために再度歩く。parser.Parse::RecDescentを使ったスクリプトがあります。二番目のパーサの文法は一番目のパーサを呼び出します。this?これは可能ですか?できます。isデータ構造があります。setsこのデータ構造は要素が配列/リストのハッシュになっています。解析できる文法もあります。ここまでは全てOKです。わからないということです。文法的に正しいかどうか決めることだけです。convenience.次の文法を試してもらいたい。これに巨大な文字列を入力する。最後に、使いやすいようこの変数も返される。hash.これは基本的にフレーズと、意味のリストを解析する。何であるか知ることができる。文字列の配列リファレンスを返す。適切なスロットに保持される。efficient...)この説明が役に立つことを願いたい。behaviour.プロダクションでオルタネーションを使っています。振る舞いが欲しいのです。ディレクティブを使っています。set.こんな感じで。Programming"のスタイルで書かれている。続いて独立したアイテムがくる"ということになる。backtracking.二つ目の方がより効率的だ。後戻り(バックトラック)がないから。change.だが、一つ目の方が可読性が高く、メンテナンスもしやすい。空規則がないからである。トップレベルで変更しなくてすむ。go.しかし、スピードがあなたの求めているものであるなら、二つ目でいくことになる。プリコンパイルオプションに目を通して欲しい。本当に大きなファイルではParse::RecDescentが遅くなる。文法が"深く"ならないようにする。入れ子のサブ規則をいくつかのレベルで用いる。代わりに正規表現の終端記号を使う。instead.マッチしたものを捕らえる¶やあ、$returnにセットされたものじゃなくてARRAY(0x355300)ってのが出てきたよ。is:この規則は間違って書かれている。2番目のポジションから@itemはTextCharを持っていると考えている。way.2番目のポジションは配列リファレンスであることに注意。ように規則を書かなければならない。effect.Parse::RecDescentを使って、トークン間の空白を補足する必要があります。変更してみました(これで空白をトークン化できます)。望むべき結果にはならないようです。sufficient.全てのスキップした空白が保持される変数さえあれば十分です。use:空白のスキップをやめて手動で操作することができる。examples.以上、例として。adding手がかりは;アクションで何かが間違っている。解析を行なっていない。以下を付け加えてみてくれ。actions.各トップレベルの規則の最後で、パースのエラーがあるかどうか教えてくれる。可能なら、何がエラーなのかも。アクションをよくみるべし。必要があるかもしれない。matching:下のケースでは、rule_oneはマッチしたスカラー値を返す。rule_towはマッチした一つの要素を持った配列リファレンスを返す。正規表現における*と+の振る舞いが、より近いモデルである。alternative:私はそれがあなたの観点に依存していると推測します。タイプによってコードがグチャグチャになることでしょう。rejectを加えたら、無条件に失敗してしまう。subrule.これはサブ規則numberに最後にマッチしたものに対応した値を返すだけだ。%itemに書かれた二通りのやり方がある。