我应该使用 Lex 还是自制解决方案来解析公式?

发布于 2024-08-16 13:51:37 字数 525 浏览 7 评论 0原文

我正在编写一个小型的、基于规则的“数学”引擎。我意识到这还不清楚,所以我将提供一个小例子。

假设你有一些变量 a,它保存一个整数。您还有一些可以应用于数字的函数,即

  • sqr - 对数字进行平方
  • flp - 翻转数字的位
  • dec - 递减数字
  • inc - 增加数字

然后您可以说,do_formula(a, "2sqr+inc+flp")。如果 a 是 3,它会将其平方两次(81),递增它(82),然后翻转它的位(〜82 - 我相信,如果处理有符号整数,则为 -83)。

解析公式的最佳方法是什么?它相对简单,我正在考虑让所有操作码都是 3 个字符......使用 Lex 会不会太过分了?我应该只编写一个简单的自制解决方案还是完全使用其他东西?

我意识到上面的例子很愚蠢;我并没有构建一个可以做到这一点的计算器,但它说明了我正在努力做得足够好。

I'm in the process of writing a small, rule-based 'math' engine. I realize this is unclear, so I'll provide a small example.

Let's say you have some variable a, that holds an integer. You also have some functions you can apply to the number, i.e.

  • sqr - square the number
  • flp - flip the bits of the number
  • dec - decrement the number
  • inc - increment the number

You can then say, do_formula(a, "2sqr+inc+flp"). If a were 3, it'd square it twice (81), increment it (82), and flip the bits of it (~82 -- which is -83, if dealing with signed integers, I believe).

What would be the best way of parsing the formula? It's relatively simple, and I'm thinking of making all the opcodes be 3 characters... would it be overkill to use Lex? Should I just write a simple home-brewed solution or use something else entirely?

I realize the above example is silly; I'm not building a calculator that'll do that, but it illustrates what I'm trying to do well enough.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

早茶月光 2024-08-23 13:51:37

如果你的语法不是超级复杂并且你不介意用 Python 来实现,pyparsing 可能是正是医生所吩咐的。我实现了一些非常类似的东西来解析化学方程式,我花了一个小时左右的时间才完成。我会在此处添加代码,但它不会特别相关。

If your grammar isn't super-complex and you don't mind doing it in Python, pyparsing could be just what the doctor ordered. I implemented something fairly similar for parsing chemical equations and it took me an hour or so to do it. I'd add the code here, but it wouldn't be particularly relevant.

皇甫轩 2024-08-23 13:51:37

是的,在这种情况下似乎有点矫枉过正。只需将字符串拆分为“=”,然后一个接一个地应用操作。感谢上帝,作为一等公民,您的引擎可以用 0.5 - 1 页代码编写。

dct = {'sqr' : lambda a: a * a, ...}

ntimes, op = token[:-3], token[-3:]
ntimes = 0 if len(ntimes) == 0 else int(ntimes)

..
dct[op](a)

Yes, seems like an overkill in this case. Just split the string on '=", and then apply the operations one after another. Thank god for dictionaries and functions as first-class citizen your engine can be written in 0.5 - 1 pages of code.

dct = {'sqr' : lambda a: a * a, ...}

ntimes, op = token[:-3], token[-3:]
ntimes = 0 if len(ntimes) == 0 else int(ntimes)

..
dct[op](a)
几度春秋 2024-08-23 13:51:37

这实际上取决于您的项目最终有多大:如果您正在考虑创建一种新语言或解析比 + 更有趣的语法的东西,那么我会说 lex 将是一种有趣且有趣的花费方式一个下午。

另一方面,如果您事先已经考虑好语法,那么编写自己的解析器会提供非常丰富的信息,而且并不是特别困难。

问题实际上最终是用哪种语言进行解析? Haskell 将是一个非常有趣的选择,当我几年前编写第一个解析器时,它为我提供了很多有趣的启示。

It really depends on how big your project is going to end up being: If you're looking at creating a new language or something that's parsing more interesting grammars than just + then I'd say lex would be a fun and entertaining way to spend an afternoon.

On the other hand, writing your own parser is extremely informative and not particularly hard if you've really thought out the grammar beforehand.

The question really ends up being which language to do the parsing in? Haskell would be a really fun choice and provided a lot of interesting revelations for me when I wrote my first parser a couple years ago.

天赋异禀 2024-08-23 13:51:37

您的宿主语言是什么?对于 Ruby,我真的很喜欢 treetop。开始有点困难,但我已经成功地使用它来解析更复杂的数学表达式。

What's your host language? For Ruby, I really like treetop. It's a bit hard to get started, but I've used it with success for parsing more complicated math expressions.

淡写薰衣草的香 2024-08-23 13:51:37

如果您有一些空闲时间并且想要学习新的编程范例,请尝试一下 Prolog!

If you have some free time and want to learn a new programming paradigm, give Prolog a spin!

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文