Advertisement
Advertisement

More Related Content

Slideshows for you(20)

Advertisement
Advertisement

Parser combinatorってなんなのさ

  1. Parser Combinatorって なんなのさ 開発解析事業部東 2014/08/21
  2. 文字列を解釈する処理 基本的に作るのが面倒 → Parser Combinatorを使って楽しよう 既存手法 補足 頑張って手書き 書くのが面倒、デバックが面倒 Parser Generator 使い方覚えるのが面倒
  3. Parser Combinator •Parser –入力: 文字列 –出力: 解析結果(数値など),読み残し文字列 •Parser Combinator –入力: 1つ以上のParser –出力: 新しいParser → 単純なParserから複雑なParserを構築
  4. 例: 計算機を作ろう 0〜9の数字,+,* のみを含む文字列から なる計算式を解釈,計算結果を返す 計算機 1 0 + 2 * 3 16 計算機 * 3 _人人人人人_ >エラー<  ̄Y^Y^Y^Y ̄
  5. 文字列、数値、Parserの表記 文字列 1 0 + 2 * 3 空 数値 16 Parser int 1 0 + 2 * 3 10 + 2 * 3 読み残し 解析結果 in out
  6. 関数、Parser Combinatorの表記 関数 Parser Combinator sum 2 1 4 7 Chain mul 2 * 3 6 空 in out in out
  7. どうやって解釈しよう? 1 0 + 2 3 4 * 5 + 6 * 7 *
  8. + 区切りで分割してみる 1 0 + 2 3 4 * 5 + 6 * 7 * 「整数が* 区切りで並んでいる文字列」が + 区切りで並んでいる
  9. 3 つのParser が必要? 1 0 + 2 3 4 * 5 + 6 * 7 * 「整数が*区切りで並んでいる文字列」が +区切りで並んでいる Integer Parser Multiple Parser Plus Parser
  10. 1 つのParser Combinatorが必要? 1 0 + 2 3 4 * 5 + 6 * 7 * 「整数が*区切りで並んでいる文字列」が +区切りで並んでいる
  11. 1 つのParser Combinatorが必要? 1 0 + 2 3 4 * 5 + 6 * 7 * 「整数が*区切りで並んでいる文字列」が +区切りで並んでいる
  12. Integer parser int 1 0 + 2 * 3 10 + 2 * 3 int 1 0 0 100 空 int + 2 * 3 _人人人人人人_ >解析失敗<  ̄Y^Y^Y^Y^Y ̄
  13. Character parser char + 2 * 3 0 2 * 3 char + 0 空 char * 3 + + + 0 0 0 _人人人人人人_ >解析失敗<  ̄Y^Y^Y^Y^Y ̄
  14. ChainCombinator Chain char int * 1 mul 2 * 3 0 * 1 •入力を右、左、右と交互にParserへ与える •左のParserで解析できなかったら解析成功
  15. ChainCombinator Chain char int * 1 mul 2 * 3 0 * 1 読み始める位置 入力を右側のparserで解釈する
  16. ChainCombinator Chain char int * 1 mul 2 * 3 0 * 1 入力を右側のparserで解析する 10
  17. ChainCombinator Chain char int * 1 mul 2 * 3 0 * 1 残りを左側のparserで解析する 10
  18. ChainCombinator Chain char int * 1 mul 2 * 3 0 * 1 残りを左側のparserで解析する 10 1
  19. ChainCombinator Chain char int * 1 mul 2 * 3 0 * 1 残りを右側のparserで解析する 10 1 2
  20. ChainCombinator Chain char int * 1 mul 2 * 3 0 * 1 残りを左側のparserで解析する 10 1 2 1
  21. ChainCombinator Chain char int * 1 mul 2 * 3 0 * 1 残りを右側のparserで解析する 10 1 2 1 3
  22. ChainCombinator Chain char int * 1 mul 2 * 3 0 * 1 残りを左側のparserで解析する→ 失敗 → (全体としては) 解析成功 10 1 2 1 3
  23. ChainCombinator Chain char int * 1 mul 2 * 3 0 * 1 途中で得られた解析結果を関数で評価して 全体の解析結果として返す 10 1 2 1 3 60 空
  24. Chain _人人人人人_ >計算機<  ̄Y^Y^Y^Y ̄ Chain char int * 1 mul sum char + 0
  25. Parser Combinator何が嬉しいの? 単純なParserから 複雑なParser を構築できる –Parser 個別のテストがしやすい –Parser の再利用性が高い –Parser Combinatorの再利用性が高い
  26. Parser CombinatorLibrary Language Library Haskell Parsec, Attoparsec F# FParsec Scala scala.util.parsing.combinator.Parsers C# Sparche, csharp-monad Python PyParsing
  27. Sparcheを用いた計算機の実装 varInt=Parse.Regex("[0-9]+").Select(int.Parse); varMul=Parse.String("*").Select(_ =>1); varPlus =Parse.String("+").Select(_ =>0); varMulExpr= Parse.ChainOperator(Mul, Int, (op, acc, elem) =>acc*elem); varPlusExpr= Parse.ChainOperator(Plus, MulExpr, (op, acc, elem) =>acc+elem); varresult = PlusExpr.Parse("10+2*3");
  28. 典型的なParser Combinator •Combine(P1, P2) P1 で解析成功したらその読み残しをP2で解析、 それも解析成功したら、解析成功 •Or(P1, P2) 1. P1で解析成功したら解析成功 2. P2で解析成功したら解析成功 3. 両方失敗したらその解析失敗 •ZeroOrMore(P) P で0回以上解析できたら成功
  29. まとめ •Parser Combinatorをざっくり説明した •利用例として簡単な計算機を定義した •Parser CombinatorLibrary を紹介した
Advertisement