python - Python AST - 检测表达式中的非法标记
问题描述
我应该如何优化compile()
函数(解析器)以:
只接受标记:
'numeric string (integer)'
,ADD
,SUB
,MUL
, 和DIV
检测带有错误显示的非法令牌/表达式(立即停止):
ERROR: Unexpected token at # 4
ADD
,SUB
,MUL
, 并且DIV
必须恰好有两个标记:
[
'numeric string (integer)'
或ADD
或SUB
或MUL
或DIV
]
和
[
'numeric string (integer)'
或ADD
或SUB
或MUL
或DIV
]
- 该函数应该从最内向的表达式开始计算表达式。
代码:
def is_operator(token):
return (token in ['ADD', 'SUB', 'MUL', 'DIV'] or token.isnumeric())
# Compiles a list of tokens
# into an abstract syntax tree (AST).
#
# A token represents either a number (e.g. "42")
# or an operator ("ADD", "SUB", "MUL" or "DIV").
#
# A node of the returned AST is either a string
# that represents a number (e.g. "42")
# or a tuple in the form of (operator, child1, child2)
# where child1 and child2 are the subtrees of the AST.
#
# This function returns (ast, unprocessed_tokens)
# where unprocessed_tokens are the tokens yet to compile.
#
def compile(tokens):
if len(tokens) == 0:
return ('NOOP',)
token = tokens[0]
if is_operator(token):
child1, unprocessed = compile(tokens[1:])
child2, unprocessed = compile(unprocessed)
return (token, child1, child2), unprocessed
else:
return token, tokens[1:]
line = ['ADD', 'SUB', '2', '2', 'MUL', '6', 'DIV', '10', '2']
print(compile(line)[0])
# => ('ADD', ('SUB', '2', '2'), ('MUL', '6', ('DIV', '10', '2')))
样品#1:
输入:
line = ['ADD', 'SUB', '3', '2', 'MUL', '6', 'DIV', '10', '2']
预期输出:
AST: ('ADD', ('SUB', '3', '2'), ('MUL', '6', ('DIV', '10', '2')))
ANSWER: 31
样品#2:
输入:
line = ['ADD', '3', '2', '1']
预期输出:
ERROR: Unexpected token at # 4
PS:
我知道解析库,我不会朝那个方向走。我需要通过使用本机 python 代码来解决它。
我已经编写了lexer()
函数。
解决方案
推荐阅读
- ajax - 构建一个基于 AJAX 的 wordpress 插件
- java - 如何在java中创建一个带有节点的通用类型的get方法
- reactjs - 在 React 中仅渲染下一个未填充的表单组件
- python - 在Python中计算日期之间的天数?
- datetime - 如何将 chrono DateTime 设置为特定的日期和时间?
- java - 为 Jackson 自定义反序列化程序抛出带有 HTTP 状态代码的自定义异常
- python - 微信评论页面有链接,但是抓包软件和get请求获取的内容不一样
- arrays - 合并来自多个工作表的表
- arrays - 从 Bash 中的标准输入文件动态填充两个数组
- android - 画布不在 SurfaceView 中绘制