【发布时间】:2010-07-29 13:56:57
【问题描述】:
我正在尝试在 Ruby 中为语法创建递归下降解析器,该语法由以下规则定义
-
输入由空格分隔的卡片组成,以停用词开头,
其中 white-space 是正则表达式
/[ \n\t]+/ - 卡片可能包含 Keywords 或/和 Values 也由空格分隔, 具有特定于卡片的顺序/模式
- 所有停用词和关键字都不区分大小写,即:
/^[a-z]+[a-z0-9]*$/i -
值可以是一个双引号的字符串,可以不分开 用空格表示的其他词,例如:
word"quoted string"word 值也可以是 word
/^[a-z]+[a-z0-9]*$/,或 integer,或 float(例如-1.15,或 @ 987654328@)-
单行注释用
#表示,可以不分开 换句话说,例如:word#single-line comment\n -
多行注释由
/*和*/表示,可能不是 与其他词分开,例如:word/*multi-line comment*/word
# Input example. Stop-words are chosen just to highlight them: set, object
set title"Input example"set objects 2#not-separated by white-space. test: "/*
set test "#/*"
object 1 shape box/* shape is a Keyword,
box is a Value. test: "#*/object 2 shape sphere
set data # message and complete are Values
0 0 0 0 1 18 18 18 1 35 35 35 72 35 35 # all numbers are Values of the Card "set"
由于大多数单词都用空格分隔,有一段时间我在考虑拆分整个输入并逐字解析。为了处理 cmets 和引号,我打算这样做
words = input_text.gsub( /([\"\#\n]|\/\*|\*\/)/, ' \1 ' ).split( /[ \t]+/ )
但是,以这种方式修改了字符串(和 cmets,如果我想保留它们)的内容。您将如何处理这些粘性 cmets 和引号?
【问题讨论】:
-
我不认为在空格上分割文本对于解析除了最简单的语法之外的任何内容都是一个好主意。我不想在这里写一篇关于创建解析器的文章......无论如何,谷歌搜索“compiler compiler ruby”,“parser generation ruby”......这是一个例子treetop.rubyforge.org
-
嗯,树顶对我来说有点难以理解。也许你能告诉我如何将它应用到我的语法中?我认为对于这么简单的语法,我可以在 SO 用户的帮助下自己制作一些东西。
标签: ruby parsing recursive-descent