パーサジェネレータ

[戻る]
亀山 2009/12/16(水) 18:52:17
ユーザがエディットボックスなどで入力した数式文字列を受け取って、
その値を計算して表示するという、電卓のような機能を作りたいと思っています
(条件演算子やsqrt()などの関数マクロも入れたい)。

ネットでいろいろ調べていたところ、「パーサジェネレータ」という、
解析クラスのソースを自動で作ってくれるソフト(?)があることを読みました。
しかし、VC上で実際に使うためのサンプルなどが見つけられず、
どのように使うべきものなのかがよく理解できていません。

どなたか、VC上のプロジェクトでパーサジェネレータを使う方法などに
お詳しいかたはいらっしゃいませんでしょうか。
お勧めのソフトや使いかたなども教えていただけると嬉しいです。
よろしくお願いします。

maru 2009/12/16(水) 20:56:43
「パーサジェネレータ」は解析クラスの「ソースを自動で作ってくれるツール」な
ので、「VC上で実際に使うため」に何か特別なことは有りません。「作成された
ソースコード」を自分で使うアプリケーションに組み込むだけです。

「VC上のプロジェクトでパーサジェネレータを使う方法」って何を期待しているん
だろう?

電卓を作るために、「パーサジェネレータ」=yaccを使う例が
http://kmaebashi.com/programmer/devlang/yacclex.html
に有りましたので参考になるかも。

tetrapod 2009/12/16(水) 21:05:31
要するに、プログラム中で任意の式解析+演算をしたいつーことでおk?

式計算のためには「逆ポーランド記法」ってやつを使うととりあえず便利で
逆ポーランド記法が何でどう使うのかは、まずはぐぐって味噌。
とりあえずこんなあたりとか。
http://www.gg.e-mansion.com/~kkatoh/program/novel2/novel207.html

構文解析を行うための C++ のクラスというと boost::spirit だったりするが
構文解析とは何かを理解しないまま spirit に手を出そうとすると
何がなんだかまったくわからん・・・ということになりそうな気がする。
1+2*3+4*5 位の式を構文解析+式計算するだけならネット上にいくらでも
サンプルが転がっているので、まずはそれを理解できるようになってから。
それでもどうしても spirit してみたいのなら
http://www.kmonos.net/alang/boost/classes/spirit.html

仲澤@失業者 2009/12/17(木) 09:48:20
折れたら、Calc.exe「=電卓」を起動して外部からコントロールすること
を検討するのもいいかもしれません。割と簡単です(^^;)。

亀山 2009/12/21(月) 09:49:33
maruさん、tetrapodさん、仲澤@失業者さん、ご意見ありがとうございます。

> 要するに、プログラム中で任意の式解析+演算をしたいつーことでおk?

そのような感じです。
四則演算のみのものなら自前で作ったこともありますし、
逆ポーランド記法も概念自体は理解しているつもりですが、
今回は一文の中に条件演算子(三項演算子?)による条件分けの機能なども必要で、
なにかよいサンプルは無いかとネット上を探していたところに
パーサジェネレータというものの存在を知り、
これを使うことができないかと調べていたところでした。

教えていただいたサイトなどをもとに、
もうちょっと理解してから実装方法を検討してみたいと思います。
ありがとうございます。

tetrapod 2009/12/21(月) 12:21:26
(E)BNF って何ぞや、が理解できて自分で記述できるのであれば
spirit は C++ の式として BNF を書くだけで俺ルールの式解析できるので
http://tamachan.club.kyutech.ac.jp/~gridbug/spirit/spirit02.html
ということになるわけだが・・・
三項演算子を定義する BNF が書ける?

spirit は今もバージョンアップしているので、
俺の紹介した参考記事は、そのままでは最新 spirit に通らないってあたりも
またいろいろ困ったチャンだったりするのよね

亀山 2009/12/26(土) 20:28:43
[[解決]]
tetrapodさん、ご意見ありがとうございます。

STL自体はほぼ未経験で、正直まだ理解や実装方法の決定ができておらず、
進捗を報告できる状態ではありませんが、どんどん下に行ってしまいますので、
いったん解決マークを付けさせていただきます。
ありがとうございます。

古いスレッドには追加発言できません。