【发布时间】:2021-01-08 14:58:08
【问题描述】:
我正在尝试从头开始为 C++ 代码制作一个非常简单的词法分析器(Tokenizer),而不使用 PLY 或任何其他库。
到目前为止我做过的事情:
- 在字典中定义关键字、运算符。
- 为注释、文字等定义了正则表达式。
我的困惑:
问题一:
现在我正在尝试创建一个函数check_line(line),它将使用一行代码并在字典中返回标记。例如:
check_line('int main()')
输出应该是:
Tokens = {'Keyword':'int', 'Keyword':'main', 'Opening parenthesis':'(','Closing Parenthesis':')'}
但我得到的输出是:
Tokens = {'Keyword':'main', 'Keyword':'main', 'Opening parenthesis':'(','Closing Parenthesis':')'}
因为 main 在这里覆盖了 int。
有没有办法解决这样的问题?
问题2:
当我在函数中传递check_line('int main()') 时,程序与main 不匹配,因为这里我们有括号。我该如何解决这个问题。
我正在粘贴我到目前为止编写的代码,请看一下并告诉我你的想法。
import re
# Keywords
keywords = ['const','float','int','struct','break',
'continue','else','for','switch','void',
'case','enum','sizeof','typedef','char',
'do','if','return','union','while','new',
'public','class','friend','main']
# Regular Expression for Identifiers
re_id = '^[_]?[a-z]*[A-Z]([a-z]*[A-Z]*[0-9]+)'
# Regular Expression for Literals
re_int_lit = '^[+-]?[0-9]+'
re_float_lit = '^[+-]?([0-9]*)\.[0-9]+'
re_string_lit = '^"[a-zA-Z0-9_ ]+"$'
# Regular expression of Comments
re_singleline_comment = '^//[a-zA-Z0-9 ]*'
re_multiline_comment = '^/\\*(.*?)\\*/'
operators = {'=':'Assignment','-':'Subtraction',
'+':'Addition','*':'Multiplication',
'/':'Division','++':'increment',
'--':'Decrement','||':'OR', '&&':'AND',
'<<':'Cout operator','>>':'Cin Operator',
';':'End of statement'}
io = {'cin':'User Input',
'cout':'User Output'}
brackets = {'[':'Open Square',']':'Close Square',
'{':'Open Curly','}':'Close Curly',
'(':'Open Small',')':'Close Small'}
# Function
def check_line(line):
tokens = {}
words = line.split(' ')
for word in words:
if word in operators.keys():
tokens['Operator ' + word] = word
if word in keywords:
tokens['Keywords'] = word
if re.match(re_singleline_comment,word):
break
return tokens
check_line('int main()')
输出:
{'Keywords': 'main'}
输出应该是:
Tokens = {'Keyword':'int', 'Keyword':'main', 'Opening parenthesis':'(','Closing Parenthesis':')'}
PS:我还没有完成条件,只是想先解决这个问题。
【问题讨论】:
-
您不能使用 split - 如果标记之间没有空格,例如
main(),则标记器将失败。您需要一次构建一个字符的令牌。在编写任何代码之前给自己画一个状态图或铁路图。如果你搜索lexical analysis state diagram,有很多例子说明如何做到这一点