├── LICENSE ├── README.md ├── error.py ├── lexical ├── lexical.py └── rule.py ├── main.py ├── semantic ├── code.py ├── rule.py └── symbol.py ├── syntax ├── rule.py └── syntax.py ├── test.c └── test.py /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2018 John Kindem 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # C(缩减版)语言编译器前端 2 | ## 是什么 3 | NUAA 2017年编译原理课设,词法分析使用正则表达式,语法分析使用LL(1)文法分析器, 4 | 语义分析使用自上而下翻译,使用 Python 语言编写,面向配置化,稍加改造可以适用其他文法 5 | 6 | ## 怎么使用 7 | ``` 8 | git clone https://github.com/FlyAndNotDown/CSub-CompilerFrontend.git 9 | ``` 10 | 在 PyCharm 中打开新建项目导入代码即可,Python 使用版本为 3 以上,请不要使用 Python2 运行该项目 11 | 12 | ## 代码结构说明 13 | * main.py 编译器主程序 14 | * error.py 存放错误相关的类和代码 15 | * test.c 要编译的文件 16 | * lexical 词法分析 17 | * syntax 语法分析 18 | * semantic 语义分析 19 | 20 | 另外,三大分析中 rule.py 即是支持编译器的所有文法、词法、语义规则,加以改动即可面向一些其他的文法和语言使用 21 | 22 | ## 关于 23 | NUAA 161520311 John Kindem 24 | -------------------------------------------------------------------------------- /error.py: -------------------------------------------------------------------------------- 1 | """ 2 | 错误 3 | """ 4 | 5 | 6 | class Error: 7 | """ 8 | 错误 9 | """ 10 | def __init__(self, error_info): 11 | """ 12 | 构造 13 | :param error_info: 错误信息 14 | """ 15 | self.info = error_info 16 | 17 | 18 | class LexicalError(Error): 19 | """ 20 | 词法错误 21 | """ 22 | def __init__(self, error_info, error_line): 23 | """ 24 | 构造 25 | :param error_info: 错误信息 26 | :param error_line: 错误行数 27 | """ 28 | super().__init__(error_info) 29 | self.line = error_line 30 | 31 | 32 | class SyntaxRuleError(Error): 33 | """ 34 | 语法分析规则错误 35 | """ 36 | def __init__(self, error_info): 37 | """ 38 | 构造 39 | :param error_info: 信息 40 | """ 41 | super().__init__(error_info) 42 | 43 | 44 | class SyntaxError(Error): 45 | """ 46 | 语法错误 47 | """ 48 | def __init__(self, error_info, error_line): 49 | """ 50 | 构造 51 | :param error_info: 错误信息 52 | :param line: 错误行数 53 | """ 54 | super().__init__(error_info) 55 | self.line = error_line 56 | 57 | 58 | class SemanticError(Error): 59 | """ 60 | 语义分析错误 61 | """ 62 | def __init__(self, info): 63 | super().__init__(info) 64 | 65 | 66 | class SemanticRuleError(Error): 67 | def __init__(self, info): 68 | super().__init__(info) -------------------------------------------------------------------------------- /lexical/lexical.py: -------------------------------------------------------------------------------- 1 | """ 2 | 词法分析器 3 | """ 4 | from lexical.rule import * 5 | from error import LexicalError 6 | import re 7 | 8 | 9 | class Token: 10 | """ 11 | Token 12 | """ 13 | def __init__(self, token_type='', token_str='', token_line=-1): 14 | """ 15 | 构造 16 | :param token_type: Token 的类型 17 | :param token_str: Token 的内容 18 | :param token_line: Token 所在行数 19 | """ 20 | self.type = token_type 21 | self.str = token_str 22 | self.line = token_line 23 | 24 | 25 | class Lexical: 26 | """ 27 | 词法分析器 28 | """ 29 | def __init__(self): 30 | """ 31 | 构造 32 | """ 33 | # 错误 34 | self.__error = None 35 | 36 | # 源代码 37 | self.__source = '' 38 | 39 | # 分隔出来的每一行 40 | self.__lines = list() 41 | 42 | # 结果 43 | self.__tokens = list() 44 | 45 | def load_source(self, source): 46 | """ 47 | 装载源代码 48 | :param source: 源代码 49 | """ 50 | self.__source = source 51 | 52 | def execute(self): 53 | """ 54 | 执行词法分析 55 | :return: 词法分析是否成功 56 | """ 57 | self.__replace_useless_chars() 58 | if self.__del_notes(): 59 | self.__split_lines() 60 | if self.__split_tokens(): 61 | self.__del_spaces() 62 | return True 63 | else: 64 | return False 65 | else: 66 | return False 67 | 68 | def get_result(self): 69 | """ 70 | 获取结果 71 | :return: token 列表 72 | """ 73 | return self.__tokens 74 | 75 | def get_error(self): 76 | """ 77 | 获取错误 78 | :return: 错误原因 79 | """ 80 | return self.__error 81 | 82 | def __replace_useless_chars(self): 83 | """ 84 | 替换无用的字符 85 | """ 86 | # 将 \r 替换成 \n 87 | self.__source = self.__source.replace('\r', '\n') 88 | # 将 \t 替换成四个空格 89 | self.__source = self.__source.replace('\t', ' ') 90 | 91 | def __del_notes(self): 92 | """ 93 | 删除注释 94 | :return: 是否删除成功 95 | """ 96 | # 计数器,用来确认注释开始符和注释结束符的数量是否相等 97 | note_count = 0 98 | # 缓冲区 99 | buffer = self.__source 100 | # 结果 101 | result = self.__source 102 | 103 | # 判断是否匹配到了末尾 104 | while True: 105 | # 尝试匹配 */ 106 | match = re.compile(regex_dict[note_char_type[0]]).search(buffer) 107 | # 如果匹配到了 108 | if match: 109 | left_note_start = match.start() 110 | # 开始匹配 */ 111 | match2 = re.compile(regex_dict[note_char_type[1]]).search(buffer) 112 | # 如果匹配到了 113 | if match2: 114 | right_note_end = match2.end() 115 | # 判断匹配到的区间中有几行 116 | line_count = result[left_note_start:right_note_end].count('\n') 117 | # 执行删除 118 | result = result.replace(result[left_note_start:right_note_end], '\n' * line_count) 119 | # 删除完毕之后进入下一次循环 120 | buffer = result 121 | continue 122 | # 如果没有匹配到,说明两者数量不匹配,报错 123 | else: 124 | # 判断错误所在的行数 125 | enter_location = list() 126 | enter_location.append(0) 127 | for i in range(0, len(result)): 128 | if result[i] == '\n': 129 | enter_location.append(i) 130 | find = False 131 | 132 | error_line = 0 133 | for i in range(0, len(enter_location) - 1): 134 | if enter_location[i] < left_note_start < enter_location[i + 1]: 135 | error_line = i + 1 136 | find = True 137 | break 138 | if not find: 139 | error_line = len(enter_location) 140 | 141 | # 报错 142 | self.__error = LexicalError('/* 没有相匹配的 */', error_line) 143 | return False 144 | # 如果没有匹配到 145 | else: 146 | # 尝试寻找有没有落单的 */ 147 | match2 = re.compile(regex_dict[note_char_type[1]]).search(buffer) 148 | # 如果找到了说明错误了 149 | if match2: 150 | right_note_start = match2.start() 151 | # 判断错误所在的行数 152 | enter_location = list() 153 | enter_location.append(0) 154 | for i in range(0, len(result)): 155 | if result[i] == '\n': 156 | enter_location.append(i) 157 | find = False 158 | 159 | error_line = 0 160 | for i in range(0, len(enter_location) - 1): 161 | if enter_location[i] < right_note_start < enter_location[i + 1]: 162 | error_line = i + 1 163 | find = True 164 | break 165 | if not find: 166 | error_line = len(enter_location) 167 | 168 | # 报错 169 | self.__error = LexicalError('多余的 */', error_line) 170 | return False 171 | # 如果没有找到那就说明已经找完了,跳出 172 | else: 173 | break 174 | 175 | # 将 result 保存到 __source 中 176 | self.__source = result 177 | return True 178 | 179 | def __split_lines(self): 180 | """ 181 | 将完成源代码分割成行序列 182 | """ 183 | # 清空 __tokens 184 | self.__tokens.clear() 185 | # 按行分割 186 | temp = self.__source.split('\n') 187 | # 将分割出来的行序列添加到 __tokens 中 188 | for t in temp: 189 | self.__lines.append(' ' + t) 190 | 191 | def __split_tokens(self): 192 | """ 193 | 从行序列中分割出 token 194 | :return: 是否分割成功 195 | """ 196 | # 先将 __lines 拷贝一份到临时变量中 197 | lines = list() 198 | for line in self.__lines: 199 | lines.append(line) 200 | # 缓冲区 201 | buffer = '' 202 | # 当前所在行数 203 | current_line_num = 0 204 | # 结果 205 | tokens = list() 206 | 207 | # 参与匹配的 type 名 208 | types = list() 209 | for i in split_char_type: 210 | types.append(i) 211 | for i in token_type: 212 | types.append(i) 213 | 214 | while len(lines) > 0: 215 | # 当前循环中是否匹配成功 216 | match_this_time = False 217 | 218 | # 如果缓冲区中没有数据了,就填充一行到缓冲区 219 | if buffer == '': 220 | buffer = lines[0] 221 | lines = lines[1:] 222 | # 行号自增 223 | current_line_num += 1 224 | 225 | # 开始匹配 226 | # 尝试用所有的正则表达式来匹配 227 | for t in types: 228 | match = re.compile(regex_dict[t]).match(buffer) 229 | # 如果匹配到了 230 | if match: 231 | # 将其添加到 tokens 中 232 | tokens.append(Token(t, buffer[match.start():match.end()], current_line_num)) 233 | # buffer 去除已经匹配的部分 234 | buffer = buffer[match.end():] 235 | match_this_time = True 236 | break 237 | # 如果匹配完所有的正则表达式都不成功 238 | if not match_this_time: 239 | # 报错 240 | self.__error = LexicalError('词法错误', current_line_num) 241 | # 返回失败 242 | return False 243 | # 循环正常结束则说明完全匹配成功,将结果保存到 __tokens 中,返回成功 244 | for token in tokens: 245 | self.__tokens.append(token) 246 | return True 247 | 248 | def __del_spaces(self): 249 | """ 250 | 删除 __tokens 中的空格 251 | """ 252 | # 新建临时变量 253 | tokens = list() 254 | # 将 __tokens 中的内容拷贝到 tokens 中 255 | for token in self.__tokens: 256 | tokens.append(token) 257 | # 清空 __tokens 258 | self.__tokens.clear() 259 | # 如果不是空格就添加进原来的 __tokens,相当于从原来的列表中去除了空格 260 | for token in tokens: 261 | if token.type != split_char_type[0]: 262 | self.__tokens.append(token) 263 | -------------------------------------------------------------------------------- /lexical/rule.py: -------------------------------------------------------------------------------- 1 | # 所有的 token 的类型 2 | token_type = [ 3 | 'else', 4 | 'if', 5 | 'int', 6 | 'return', 7 | 'void', 8 | 'while', 9 | 'addition', 10 | 'subtraction', 11 | 'multiplication', 12 | 'division', 13 | 'bigger', 14 | 'bigger-equal', 15 | 'smaller', 16 | 'smaller-equal', 17 | 'equal', 18 | 'not-equal', 19 | 'evaluate', 20 | 'semicolon', 21 | 'comma', 22 | 'left-parentheses', 23 | 'right-parentheses', 24 | 'left-bracket', 25 | 'right-bracket', 26 | 'left-brace', 27 | 'right-brace', 28 | 'id', 29 | 'num' 30 | ] 31 | 32 | # 分隔符号 33 | split_char_type = [ 34 | 'space' 35 | ] 36 | 37 | # 注释 38 | note_char_type = ( 39 | 'note-start', 40 | 'note-end' 41 | ) 42 | 43 | # 正则表达式字典 44 | regex_dict = { 45 | 'space': r' +', 46 | 'note-start': r'/\*', 47 | 'note-end': r'\*/', 48 | 'else': r'else', 49 | 'if': r'if', 50 | 'int': r'int', 51 | 'return': r'return', 52 | 'void': r'void', 53 | 'while': r'while', 54 | 'addition': r'\+', 55 | 'subtraction': r'-', 56 | 'multiplication': r'\*', 57 | 'division': r'/', 58 | 'bigger': r'>', 59 | 'bigger-equal': r'>=', 60 | 'smaller': r'<', 61 | 'smaller-equal': r'<=', 62 | 'equal': r'==', 63 | 'not-equal': r'!=', 64 | 'evaluate': r'=', 65 | 'semicolon': r';', 66 | 'comma': r',', 67 | 'left-parentheses': r'\(', 68 | 'right-parentheses': r'\)', 69 | 'left-bracket': r'\[', 70 | 'right-bracket': r'\]', 71 | 'left-brace': r'\{', 72 | 'right-brace': r'\}', 73 | 'id': r'[a-zA-Z][a-zA-Z]*', 74 | 'num': r'[1-9][0-9]*|0' 75 | } 76 | -------------------------------------------------------------------------------- /main.py: -------------------------------------------------------------------------------- 1 | """ 2 | 主程序 3 | """ 4 | from lexical.lexical import Lexical 5 | from syntax.syntax import Syntax 6 | 7 | 8 | # 新建词法分析器 9 | lexical = Lexical() 10 | # 载入源代码 11 | lexical.load_source(open('test.c').read()) 12 | # 执行词法分析 13 | lexical_success = lexical.execute() 14 | # 打印结果 15 | print('词法分析是否成功:\t', lexical_success) 16 | if lexical_success: 17 | lexical_result = lexical.get_result() 18 | print() 19 | print('词法分析结果:') 20 | for i in lexical_result: 21 | print(i.type, i.str, i.line) 22 | print() 23 | 24 | # 开始执行语法分析 25 | syntax = Syntax() 26 | syntax.put_source(lexical_result) 27 | syntax_success = syntax.execute() 28 | print('语法分析和语义分析是否成功\t', syntax_success) 29 | if syntax_success: 30 | print() 31 | print('语义分析结果:\t') 32 | print('三地址代码:\t') 33 | i = -1 34 | for code in syntax.get_result().root.code: 35 | i += 1 36 | print(i, ' \t', code) 37 | else: 38 | print('错误原因:\t', syntax.get_error().info, syntax.get_error().line, '行') 39 | else: 40 | print('错误原因:\t', lexical.get_error().info) 41 | -------------------------------------------------------------------------------- /semantic/code.py: -------------------------------------------------------------------------------- 1 | current_var_num = 0 2 | current_block_num = 0 3 | 4 | 5 | def get_temp_var_name(): 6 | """ 7 | 获取一个新的临时变量名 8 | :return: 临时变量名 9 | """ 10 | global current_var_num 11 | name = '_v' + str(current_var_num) 12 | current_var_num += 1 13 | return name 14 | 15 | 16 | def get_temp_block_name(): 17 | """ 18 | 获取一个新的代码块名 19 | :return: 代码块名 20 | """ 21 | global current_block_num 22 | name = '__b' + str(current_block_num) 23 | current_block_num += 1 24 | return name 25 | -------------------------------------------------------------------------------- /semantic/rule.py: -------------------------------------------------------------------------------- 1 | from semantic.symbol import * 2 | from error import SemanticError 3 | from semantic.code import get_temp_block_name, get_temp_var_name 4 | 5 | 6 | """ 7 | 添加语义规则的文法 8 | 0. program{code} ->{.init} define-list 9 | 1. define-list{code} -> define define-list 10 | {code} | empty 11 | 2. define{code} -> type ID define-type{type id} 12 | 3. define-type{code .enter} ->{.judge} var-define-follow{type id} 13 | {code} |{.judge} fun-define-follow{type fun} 14 | 4. var-define-follow{type} -> ; 15 | {type length} | [ NUM ] ; 16 | 5. type ->{type} int 17 | |{type} void 18 | 6. fun-define-follow{code} -> ( params{type fun} ) code-block{fun} 19 | 7. params{.create} -> param-list{fun} 20 | {.create} | empty 21 | 8. param-list -> param{fun} param-follow{fun} 22 | 9. param-follow -> , param{fun} param-follow{fun} 23 | | empty 24 | 10. param -> type ID array-subscript 25 | 11. array-subscript{type} -> [ ] 26 | {type} | empty 27 | 12. code-block{code} -> { local-define-list{fun} code-list{fun} } 28 | 13. local-define-list -> local-var-define{fun} local-define-list{fun} 29 | | empty 30 | 14. local-var-define -> type ID var-define-follow 31 | 15. code-list{code} -> code{fun} code-list{fun} 32 | | empty 33 | 16. code{code} -> normal-statement{fun} 34 | | selection-statement{fun} 35 | | iteration-statement{fun} 36 | | return-statement{fun} 37 | 17. normal-statement -> ; 38 | | ID normal-statement-follow{fun id} 39 | 18. normal-statement-follow{code} -> var-follow{fun} = expression{fun} ; 40 | {code} | call-follow{fun id} ; 41 | 19. call-follow{code} -> ( call-params{fun id} ) 42 | 20. call-params{code} -> call-param-list{fun} 43 | | empty 44 | 21. call-param-list{num code} -> expression{fun} call-param-follow{fun} 45 | 22. call-param-follow{num code names} -> , expression{fun} call-param-follow{fun} 46 | | empty 47 | 23. selection-statement{code} -> if ( expression{fun} ) { code-list{fun} } selection-follow{fun} 48 | 24. selection-follow{code} -> else { code-list{fun} } 49 | {code} | empty 50 | 25. iteration-statement -> while ( expression{fun} ) iteration-follow{fun} 51 | 26. iteration-follow{code} -> { code-list{fun} } 52 | {code} | code{fun} 53 | 27. return-statement{code} -> return return-follow{fun} 54 | 28. return-follow -> ; 55 | | expression{fun} ; 56 | 29. var-follow{code name type} -> [ expression{fun} ] 57 | {type} | empty 58 | 30. expression{code name bool} -> additive-expr{fun} expression-follow{fun} 59 | 31. expression-follow{bool code op name} -> rel-op additive-expr{fun} 60 | {bool} | empty 61 | 32. rel-op{op} -> <= 62 | | < 63 | | > 64 | | >= 65 | | == 66 | | != 67 | 33. additive-expr{name code} -> term{fun} additive-expr-follow{fun} 68 | 34. additive-expr-follow{add op code name} -> add-op term{fun} additive-expr-follow{fun} 69 | {add} | empty 70 | 35. add-op{op} -> + 71 | | - 72 | 36. term{name code} -> factor{fun} term-follow{fun} 73 | 37. term-follow{mul op code name} -> mul-op factor{fun} term-follow{fun} 74 | {mul} | empty 75 | 38. mul-op{op} -> * 76 | | / 77 | 39. factor{name code} -> ( expression{fun} ) 78 | | ID id-factor-follow{id fun} 79 | | NUM 80 | 40. id-factor-follow -> var-follow{fun} 81 | | ( args{fun} ) 82 | 41. args{code num} -> arg-list{fun} 83 | | empty 84 | 42. arg-list{code num} -> expression{fun} arg-list-follow{fun} 85 | 43. arg-list-follow{code num names} -> , expression{fun} arg-list-follow{fun} 86 | | empty 87 | """ 88 | 89 | 90 | # 定义一个符号表池,每次调用函数的时候使用深拷贝从这里取局部变量表 91 | symbol_table_pool = SymbolTablePool() 92 | 93 | 94 | class SemanticRule: 95 | """ 96 | 语义规则 97 | """ 98 | def __init__(self, node): 99 | """ 100 | 构造 101 | :param node: 树节点 102 | """ 103 | self.node = node 104 | self.errors = list() 105 | 106 | def __rule(self, node): 107 | """ 108 | 实际的语义规则,需要复写 109 | :param node: 110 | """ 111 | return [] 112 | 113 | def execute(self): 114 | """ 115 | 执行语义规则 116 | """ 117 | self.__rule(self.node) 118 | 119 | def have_no_errors(self): 120 | """ 121 | 是否没有错误 122 | :return: 是否没有错误 123 | """ 124 | return len(self.errors) == 0 125 | 126 | 127 | class SemanticRuleFactory: 128 | """ 129 | 语义规则工厂,根据给出的 rule_key 返回相应的实例 130 | """ 131 | @classmethod 132 | def get_instance(cls, rule_key, node): 133 | """ 134 | 获取语义规则实例 135 | :param rule_key: 关键字 136 | :param node: 目标节点 137 | :return: 实例 138 | """ 139 | # 0 140 | if rule_key == 'Program0S': 141 | return Program0S(node) 142 | if rule_key == 'Program0E': 143 | return Program0E(node) 144 | 145 | # 1 146 | if rule_key == 'DefineList0E': 147 | return DefineList0E(node) 148 | if rule_key == 'DefineList1E': 149 | return DefineList1E(node) 150 | 151 | # 2 152 | if rule_key == 'Define0E': 153 | return Define0E(node) 154 | if rule_key == 'Define0C2': 155 | return Define0C2(node) 156 | 157 | # 3 158 | if rule_key == 'DefineType0S': 159 | return DefineType0S(node) 160 | if rule_key == 'DefineType0E': 161 | return DefineType0E(node) 162 | if rule_key == 'DefineType0C0': 163 | return DefineType0C0(node) 164 | if rule_key == 'DefineType1S': 165 | return DefineType1S(node) 166 | if rule_key == 'DefineType1C0': 167 | return DefineType1C0(node) 168 | if rule_key == 'DefineType1E': 169 | return DefineType1E(node) 170 | 171 | # 4 172 | if rule_key == 'VarDefineFollow0E': 173 | return VarDefineFollow0E(node) 174 | if rule_key == 'VarDefineFollow1E': 175 | return VarDefineFollow1E(node) 176 | 177 | # 5 178 | if rule_key == 'Type0S': 179 | return Type0S(node) 180 | if rule_key == 'Type1S': 181 | return Type1S(node) 182 | 183 | # 6 184 | if rule_key == 'FunDefineFollow0E': 185 | return FunDefineFollow0E(node) 186 | if rule_key == 'FunDefineFollow0C1': 187 | return FunDefineFollow0C1(node) 188 | if rule_key == 'FunDefineFollow0C3': 189 | return FunDefineFollow0C3(node) 190 | 191 | # 7 192 | if rule_key == 'Params0S': 193 | return Params0S(node) 194 | if rule_key == 'Params0C0': 195 | return Params0C0(node) 196 | if rule_key == 'Params1S': 197 | return Params1S(node) 198 | 199 | # 8 200 | if rule_key == 'ParamList0C0': 201 | return ParamList0C0(node) 202 | if rule_key == 'ParamList0C1': 203 | return ParamList0C1(node) 204 | 205 | # 9 206 | if rule_key == 'ParamFollow0C1': 207 | return ParamFollow0C1(node) 208 | if rule_key == 'ParamFollow0C2': 209 | return ParamFollow0C2(node) 210 | 211 | # 10 212 | if rule_key == 'Param0E': 213 | return Param0E(node) 214 | 215 | # 11 216 | if rule_key == 'ArraySubscript0S': 217 | return ArraySubscript0S(node) 218 | if rule_key == 'ArraySubscript1S': 219 | return ArraySubscript1S(node) 220 | 221 | # 12 222 | if rule_key == 'CodeBlock0E': 223 | return CodeBlock0E(node) 224 | if rule_key == 'CodeBlock0C1': 225 | return CodeBlock0C1(node) 226 | if rule_key == 'CodeBlock0C2': 227 | return CodeBlock0C2(node) 228 | 229 | # 13 230 | if rule_key == 'LocalDefineList0C0': 231 | return LocalDefineList0C0(node) 232 | if rule_key == 'LocalDefineList0C1': 233 | return LocalDefineList0C1(node) 234 | 235 | # 14 236 | if rule_key == 'LocalVarDefine0E': 237 | return LocalVarDefine0E(node) 238 | 239 | # 15 240 | if rule_key == 'CodeList0E': 241 | return CodeList0E(node) 242 | if rule_key == 'CodeList0C0': 243 | return CodeList0C0(node) 244 | if rule_key == 'CodeList0C1': 245 | return CodeList0C1(node) 246 | if rule_key == 'CodeList1E': 247 | return CodeList1E(node) 248 | 249 | # 16 250 | if rule_key == 'Code0E': 251 | return Code0E(node) 252 | if rule_key == 'Code0C0': 253 | return Code0C0(node) 254 | if rule_key == 'Code1E': 255 | return Code1E(node) 256 | if rule_key == 'Code1C0': 257 | return Code1C0(node) 258 | if rule_key == 'Code2E': 259 | return Code2E(node) 260 | if rule_key == 'Code2C0': 261 | return Code2C0(node) 262 | if rule_key == 'Code3E': 263 | return Code3E(node) 264 | if rule_key == 'Code3C0': 265 | return Code3C0(node) 266 | 267 | # 17 268 | if rule_key == 'NormalStatement0E': 269 | return NormalStatement0E(node) 270 | if rule_key == 'NormalStatement1E': 271 | return NormalStatement1E(node) 272 | if rule_key == 'NormalStatement1C1': 273 | return NormalStatement1C1(node) 274 | 275 | # 18 276 | if rule_key == 'NormalStatementFollow0E': 277 | return NormalStatementFollow0E(node) 278 | if rule_key == 'NormalStatementFollow0C0': 279 | return NormalStatementFollow0C0(node) 280 | if rule_key == 'NormalStatementFollow0C2': 281 | return NormalStatementFollow0C2(node) 282 | if rule_key == 'NormalStatementFollow1E': 283 | return NormalStatementFollow1E(node) 284 | if rule_key == 'NormalStatementFollow1C0': 285 | return NormalStatementFollow1C0(node) 286 | 287 | # 19 288 | if rule_key == 'CallFollow0E': 289 | return CallFollow0E(node) 290 | if rule_key == 'CallFollow0C1': 291 | return CallFollow0C1(node) 292 | 293 | # 20 294 | if rule_key == 'CallParams0E': 295 | return CallParams0E(node) 296 | if rule_key == 'CallParams0C0': 297 | return CallParams0C0(node) 298 | if rule_key == 'CallParams1E': 299 | return CallParams1E(node) 300 | 301 | # 21 302 | if rule_key == 'CallParamList0E': 303 | return CallParamList0E(node) 304 | if rule_key == 'CallParamList0C0': 305 | return CallParamList0C0(node) 306 | if rule_key == 'CallParamList0C1': 307 | return CallParamList0C1(node) 308 | 309 | # 22 310 | if rule_key == 'CallParamFollow0E': 311 | return CallParamFollow0E(node) 312 | if rule_key == 'CallParamFollow0C1': 313 | return CallParamFollow0C1(node) 314 | if rule_key == 'CallParamFollow0C2': 315 | return CallParamFollow0C2(node) 316 | if rule_key == 'CallParamFollow1E': 317 | return CallParamFollow1E(node) 318 | 319 | # 23 320 | if rule_key == 'SelectionStatement0E': 321 | return SelectionStatement0E(node) 322 | if rule_key == 'SelectionStatement0C2': 323 | return SelectionStatement0C2(node) 324 | if rule_key == 'SelectionStatement0C5': 325 | return SelectionStatement0C5(node) 326 | if rule_key == 'SelectionStatement0C7': 327 | return SelectionStatement0C7(node) 328 | 329 | # 24 330 | if rule_key == 'SelectionFollow0E': 331 | return SelectionFollow0E(node) 332 | if rule_key == 'SelectionFollow0C2': 333 | return SelectionFollow0C2(node) 334 | if rule_key == 'SelectionFollow1E': 335 | return SelectionFollow1E(node) 336 | 337 | # 25 338 | if rule_key == 'IterationStatement0E': 339 | return IterationStatement0E(node) 340 | if rule_key == 'IterationStatement0C2': 341 | return IterationStatement0C2(node) 342 | if rule_key == 'IterationStatement0C4': 343 | return IterationStatement0C4(node) 344 | 345 | # 26 346 | if rule_key == 'IterationFollow0E': 347 | return IterationFollow0E(node) 348 | if rule_key == 'IterationFollow0C1': 349 | return IterationFollow0C1(node) 350 | if rule_key == 'IterationFollow1E': 351 | return IterationFollow1E(node) 352 | if rule_key == 'IterationFollow1C0': 353 | return IterationFollow1C0(node) 354 | 355 | # 27 356 | if rule_key == 'ReturnStatement0E': 357 | return ReturnStatement0E(node) 358 | if rule_key == 'ReturnStatement0C1': 359 | return ReturnStatement0C1(node) 360 | 361 | # 28 362 | if rule_key == 'ReturnFollow0E': 363 | return ReturnFollow0E(node) 364 | if rule_key == 'ReturnFollow1E': 365 | return ReturnFollow1E(node) 366 | if rule_key == 'ReturnFollow1C0': 367 | return ReturnFollow1C0(node) 368 | 369 | # 29 370 | if rule_key == 'VarFollow0E': 371 | return VarFollow0E(node) 372 | if rule_key == 'VarFollow0C1': 373 | return VarFollow0C1(node) 374 | if rule_key == 'VarFollow1E': 375 | return VarFollow1E(node) 376 | 377 | # 30 378 | if rule_key == 'Expression0E': 379 | return Expression0E(node) 380 | if rule_key == 'Expression0C0': 381 | return Expression0C0(node) 382 | if rule_key == 'Expression0C1': 383 | return Expression0C1(node) 384 | 385 | # 31 386 | if rule_key == 'ExpressionFollow0E': 387 | return ExpressionFollow0E(node) 388 | if rule_key == 'ExpressionFollow0C1': 389 | return ExpressionFollow0C1(node) 390 | if rule_key == 'ExpressionFollow1E': 391 | return ExpressionFollow1E(node) 392 | 393 | # 32 394 | if rule_key == 'RelOp0E': 395 | return RelOp0E(node) 396 | if rule_key == 'RelOp1E': 397 | return RelOp1E(node) 398 | if rule_key == 'RelOp2E': 399 | return RelOp2E(node) 400 | if rule_key == 'RelOp3E': 401 | return RelOp3E(node) 402 | if rule_key == 'RelOp4E': 403 | return RelOp4E(node) 404 | if rule_key == 'RelOp5E': 405 | return RelOp5E(node) 406 | 407 | # 33 408 | if rule_key == 'AdditiveExpr0E': 409 | return AdditiveExpr0E(node) 410 | if rule_key == 'AdditiveExpr0C0': 411 | return AdditiveExpr0C0(node) 412 | if rule_key == 'AdditiveExpr0C1': 413 | return AdditiveExpr0C1(node) 414 | 415 | # 34 416 | if rule_key == 'AdditiveExprFollow0E': 417 | return AdditiveExprFollow0E(node) 418 | if rule_key == 'AdditiveExprFollow0C1': 419 | return AdditiveExprFollow0C1(node) 420 | if rule_key == 'AdditiveExprFollow0C2': 421 | return AdditiveExprFollow0C2(node) 422 | if rule_key == 'AdditiveExprFollow1E': 423 | return AdditiveExprFollow1E(node) 424 | 425 | # 35 426 | if rule_key == 'AddOp0E': 427 | return AddOp0E(node) 428 | if rule_key == 'AddOp1E': 429 | return AddOp1E(node) 430 | 431 | # 36 432 | if rule_key == 'Term0E': 433 | return Term0E(node) 434 | if rule_key == 'Term0C0': 435 | return Term0C0(node) 436 | if rule_key == 'Term0C1': 437 | return Term0C1(node) 438 | 439 | # 37 440 | if rule_key == 'TermFollow0E': 441 | return TermFollow0E(node) 442 | if rule_key == 'TermFollow0C1': 443 | return TermFollow0C1(node) 444 | if rule_key == 'TermFollow0C2': 445 | return TermFollow0C2(node) 446 | 447 | # 38 448 | if rule_key == 'MulOp0E': 449 | return MulOp0E(node) 450 | if rule_key == 'MulOp1E': 451 | return MulOp1E(node) 452 | 453 | # 39 454 | if rule_key == 'Factor0E': 455 | return Factor0E(node) 456 | if rule_key == 'Factor0C1': 457 | return Factor0C1(node) 458 | if rule_key == 'Factor1E': 459 | return Factor1E(node) 460 | if rule_key == 'Factor1C1': 461 | return Factor1C1(node) 462 | if rule_key == 'Factor2E': 463 | return Factor2E(node) 464 | 465 | # 40 466 | if rule_key == 'IdFactorFollow0E': 467 | return IdFactorFollow0E(node) 468 | if rule_key == 'IdFactorFollow1E': 469 | return IdFactorFollow1E(node) 470 | if rule_key == 'IdFactorFollow1C1': 471 | return IdFactorFollow1C1(node) 472 | 473 | # 41 474 | if rule_key == 'Args0E': 475 | return Args0E(node) 476 | if rule_key == 'Args0C0': 477 | return Args0C0(node) 478 | if rule_key == 'Args1E': 479 | return Args1E(node) 480 | 481 | # 42 482 | if rule_key == 'ArgList0E': 483 | return ArgList0E(node) 484 | if rule_key == 'ArgList0C0': 485 | return ArgList0C0(node) 486 | if rule_key == 'ArgList0C1': 487 | return ArgList0C1(node) 488 | 489 | # 43 490 | if rule_key == 'ArgListFollow0E': 491 | return ArgListFollow0E(node) 492 | if rule_key == 'ArgListFollow0C1': 493 | return ArgListFollow0C1(node) 494 | if rule_key == 'ArgListFollow0C2': 495 | return ArgListFollow0C2(node) 496 | if rule_key == 'ArgListFollow1E': 497 | return ArgListFollow1E(node) 498 | 499 | return None 500 | 501 | # S 产生式开始 502 | # E 产生式结束 503 | # CN 产生式第N个元素应用之后 504 | 505 | 506 | # 0 507 | class Program0S(SemanticRule): 508 | def __rule(self, node): 509 | symbol_table_pool.init() 510 | 511 | def execute(self): 512 | self.__rule(self.node) 513 | 514 | 515 | class Program0E(SemanticRule): 516 | def __rule(self, node): 517 | for c in node.children[0].code: 518 | node.code.append(c) 519 | 520 | def execute(self): 521 | self.__rule(self.node) 522 | 523 | 524 | # 1 525 | class DefineList0E(SemanticRule): 526 | def __rule(self, node): 527 | for c in node.children[0].code: 528 | node.code.append(c) 529 | for c in node.children[1].code: 530 | node.code.append(c) 531 | 532 | def execute(self): 533 | self.__rule(self.node) 534 | 535 | 536 | class DefineList1E(SemanticRule): 537 | def __rule(self, node): 538 | node.code.clear() 539 | 540 | def execute(self): 541 | self.__rule(self.node) 542 | 543 | 544 | # 2 545 | class Define0E(SemanticRule): 546 | def __rule(self, node): 547 | for c in node.children[2].code: 548 | node.code.append(c) 549 | 550 | def execute(self): 551 | self.__rule(self.node) 552 | 553 | 554 | class Define0C2(SemanticRule): 555 | def __rule(self, node): 556 | node.type = node.get_pre_brother(2).type 557 | node.id = node.get_pre_brother(1).lexical 558 | 559 | def execute(self): 560 | self.__rule(self.node) 561 | 562 | 563 | # 3 564 | class DefineType0S(SemanticRule): 565 | def execute(self): 566 | self.__rule(self.node) 567 | 568 | def __rule(self, node): 569 | # 检查 type 是否是 void 570 | if node.type == 'void': 571 | self.errors.append(SemanticError('变量' + node.id + '不能定义为void类型')) 572 | if node.type == 'int': 573 | # 检查是否重定义 574 | if symbol_table_pool.global_var_table.exist(node.id): 575 | self.errors.append(SemanticError('变量' + node.id + '重定义')) 576 | 577 | 578 | class DefineType0E(SemanticRule): 579 | def execute(self): 580 | self.__rule(self.node) 581 | 582 | def __rule(self, node): 583 | if node.children[0].type == 'var': 584 | symbol_table_pool.global_var_table.append( 585 | GlobalVar(node.id, 'int', 4) 586 | ) 587 | if node.children[0].type == 'array': 588 | symbol_table_pool.global_var_table.append( 589 | GlobalVar(node.id, 'array', 4 * node.children[0].length) 590 | ) 591 | 592 | 593 | class DefineType0C0(SemanticRule): 594 | def execute(self): 595 | self.__rule(self.node) 596 | 597 | def __rule(self, node): 598 | node.type = node.parent.type 599 | node.id = node.parent.id 600 | 601 | 602 | class DefineType1S(SemanticRule): 603 | def execute(self): 604 | self.__rule(self.node) 605 | 606 | def __rule(self, node): 607 | # 检查是否重定义 608 | if symbol_table_pool.fun_table.exist(node.id): 609 | self.errors.append(SemanticError('函数名' + node.id + '重定义')) 610 | 611 | 612 | class DefineType1C0(SemanticRule): 613 | def execute(self): 614 | self.__rule(self.node) 615 | 616 | def __rule(self, node): 617 | node.type = node.parent.type 618 | node.fun = node.parent.id 619 | 620 | 621 | class DefineType1E(SemanticRule): 622 | def execute(self): 623 | self.__rule(self.node) 624 | 625 | def __rule(self, node): 626 | for c in node.children[0].code: 627 | node.code.append(c) 628 | 629 | 630 | # 4 631 | class VarDefineFollow0E(SemanticRule): 632 | def execute(self): 633 | self.__rule(self.node) 634 | 635 | def __rule(self, node): 636 | node.type = 'var' 637 | 638 | 639 | class VarDefineFollow1E(SemanticRule): 640 | def execute(self): 641 | self.__rule(self.node) 642 | 643 | def __rule(self, node): 644 | node.type = 'array' 645 | node.length = node.children[1].lexical 646 | 647 | 648 | # 5 649 | class Type0S(SemanticRule): 650 | def execute(self): 651 | self.__rule(self.node) 652 | 653 | def __rule(self, node): 654 | node.type = 'int' 655 | 656 | 657 | class Type1S(SemanticRule): 658 | def execute(self): 659 | self.__rule(self.node) 660 | 661 | def __rule(self, node): 662 | node.type = 'void' 663 | 664 | 665 | # 6 666 | class FunDefineFollow0E(SemanticRule): 667 | def execute(self): 668 | self.__rule(self.node) 669 | 670 | def __rule(self, node): 671 | for c in node.children[3].code: 672 | node.code.append(c) 673 | 674 | 675 | class FunDefineFollow0C1(SemanticRule): 676 | def execute(self): 677 | self.__rule(self.node) 678 | 679 | def __rule(self, node): 680 | node.type = node.parent.type 681 | node.fun = node.parent.fun 682 | 683 | 684 | class FunDefineFollow0C3(SemanticRule): 685 | def execute(self): 686 | self.__rule(self.node) 687 | 688 | def __rule(self, node): 689 | node.fun = node.parent.fun 690 | 691 | 692 | # 7 693 | class Params0S(SemanticRule): 694 | def execute(self): 695 | self.__rule(self.node) 696 | 697 | def __rule(self, node): 698 | symbol_table_pool.append( 699 | LocalVarTable(node.fun, symbol_table_pool.global_var_table) 700 | ) 701 | symbol_table_pool.fun_table.append( 702 | Fun(node.fun, node.type, symbol_table_pool.query(node.fun)) 703 | ) 704 | 705 | 706 | class Params0C0(SemanticRule): 707 | def execute(self): 708 | self.__rule(self.node) 709 | 710 | def __rule(self, node): 711 | node.fun = node.parent.fun 712 | 713 | 714 | class Params1S(SemanticRule): 715 | def execute(self): 716 | self.__rule(self.node) 717 | 718 | def __rule(self, node): 719 | symbol_table_pool.append( 720 | LocalVarTable(node.fun, symbol_table_pool.global_var_table) 721 | ) 722 | symbol_table_pool.fun_table.append( 723 | Fun(node.fun, node.type, symbol_table_pool.query(node.fun)) 724 | ) 725 | 726 | 727 | # 8 728 | class ParamList0C0(SemanticRule): 729 | def execute(self): 730 | self.__rule(self.node) 731 | 732 | def __rule(self, node): 733 | node.fun = node.parent.fun 734 | 735 | 736 | class ParamList0C1(SemanticRule): 737 | def execute(self): 738 | self.__rule(self.node) 739 | 740 | def __rule(self, node): 741 | node.fun = node.parent.fun 742 | 743 | 744 | # 9 745 | class ParamFollow0C1(SemanticRule): 746 | def execute(self): 747 | self.__rule(self.node) 748 | 749 | def __rule(self, node): 750 | node.fun = node.parent.fun 751 | 752 | 753 | class ParamFollow0C2(SemanticRule): 754 | def execute(self): 755 | self.__rule(self.node) 756 | 757 | def __rule(self, node): 758 | node.fun = node.parent.fun 759 | 760 | 761 | # 10 762 | class Param0E(SemanticRule): 763 | def execute(self): 764 | self.__rule(self.node) 765 | 766 | def __rule(self, node): 767 | # 先判断 type 是否为 void 768 | if node.children[0].type == 'void': 769 | self.errors.append(SemanticError('参数' + node.children[1].lexical + '不能定义为void类型')) 770 | if node.children[0].type == 'int': 771 | # 判断是否重定义 772 | if symbol_table_pool.query(node.fun).exist(node.children[1].lexical): 773 | self.errors.append(SemanticError('参数' + node.children[1].lexical + '重定义')) 774 | else: 775 | if node.children[2].type == 'array': 776 | symbol_table_pool.query(node.fun).append( 777 | LocalVar(node.children[1].lexical, 'address', 4, True) 778 | ) 779 | if node.children[2].type == 'var': 780 | symbol_table_pool.query(node.fun).append( 781 | LocalVar(node.children[1].lexical, 'int', 4, True) 782 | ) 783 | 784 | 785 | # 11 786 | class ArraySubscript0S(SemanticRule): 787 | def execute(self): 788 | self.__rule(self.node) 789 | 790 | def __rule(self, node): 791 | node.type = 'array' 792 | 793 | 794 | class ArraySubscript1S(SemanticRule): 795 | def execute(self): 796 | self.__rule(self.node) 797 | 798 | def __rule(self, node): 799 | node.type = 'var' 800 | 801 | 802 | # 12 803 | class CodeBlock0E(SemanticRule): 804 | def execute(self): 805 | self.__rule(self.node) 806 | 807 | def __rule(self, node): 808 | node.code.append(node.fun + ':') 809 | for c in node.children[2].code: 810 | node.code.append(c) 811 | 812 | 813 | class CodeBlock0C1(SemanticRule): 814 | def execute(self): 815 | self.__rule(self.node) 816 | 817 | def __rule(self, node): 818 | node.fun = node.parent.fun 819 | 820 | 821 | class CodeBlock0C2(SemanticRule): 822 | def execute(self): 823 | self.__rule(self.node) 824 | 825 | def __rule(self, node): 826 | node.fun = node.parent.fun 827 | 828 | 829 | # 13 830 | class LocalDefineList0C0(SemanticRule): 831 | def execute(self): 832 | self.__rule(self.node) 833 | 834 | def __rule(self, node): 835 | node.fun = node.parent.fun 836 | 837 | 838 | class LocalDefineList0C1(SemanticRule): 839 | def execute(self): 840 | self.__rule(self.node) 841 | 842 | def __rule(self, node): 843 | node.fun = node.parent.fun 844 | 845 | 846 | # 14 847 | class LocalVarDefine0E(SemanticRule): 848 | def execute(self): 849 | self.__rule(self.node) 850 | 851 | def __rule(self, node): 852 | if node.children[0].type == 'void': 853 | self.errors.append(SemanticError('变量' + node.children[1].lexical + '不能定义为void类型')) 854 | if node.children[0].type == 'int': 855 | if symbol_table_pool.query(node.fun).exist(node.children[1].lexical): 856 | self.errors.append(SemanticError('变量' + node.children[1].lexical + '重定义')) 857 | else: 858 | if node.children[2].type == 'var': 859 | symbol_table_pool.query(node.fun).append( 860 | LocalVar(node.children[1].lexical, 'int', 4, False) 861 | ) 862 | if node.children[2].type == 'array': 863 | symbol_table_pool.query(node.fun).append( 864 | LocalVar(node.children[1].lexical, 'array', 4 * node.children[2].length, False) 865 | ) 866 | 867 | 868 | # 15 869 | class CodeList0E(SemanticRule): 870 | def execute(self): 871 | self.__rule(self.node) 872 | 873 | def __rule(self, node): 874 | for c in node.children[0].code: 875 | node.code.append(c) 876 | for c in node.children[1].code: 877 | node.code.append(c) 878 | 879 | 880 | class CodeList0C0(SemanticRule): 881 | def execute(self): 882 | self.__rule(self.node) 883 | 884 | def __rule(self, node): 885 | node.fun = node.parent.fun 886 | 887 | 888 | class CodeList0C1(SemanticRule): 889 | def execute(self): 890 | self.__rule(self.node) 891 | 892 | def __rule(self, node): 893 | node.fun = node.parent.fun 894 | 895 | 896 | class CodeList1E(SemanticRule): 897 | def execute(self): 898 | self.__rule(self.node) 899 | 900 | def __rule(self, node): 901 | node.code.clear() 902 | 903 | 904 | # 16 905 | class Code0E(SemanticRule): 906 | def execute(self): 907 | self.__rule(self.node) 908 | 909 | def __rule(self, node): 910 | for c in node.children[0].code: 911 | node.code.append(c) 912 | 913 | 914 | class Code0C0(SemanticRule): 915 | def execute(self): 916 | self.__rule(self.node) 917 | 918 | def __rule(self, node): 919 | node.fun = node.parent.fun 920 | 921 | 922 | class Code1E(SemanticRule): 923 | def execute(self): 924 | self.__rule(self.node) 925 | 926 | def __rule(self, node): 927 | for c in node.children[0].code: 928 | node.code.append(c) 929 | 930 | 931 | class Code1C0(SemanticRule): 932 | def execute(self): 933 | self.__rule(self.node) 934 | 935 | def __rule(self, node): 936 | node.fun = node.parent.fun 937 | 938 | 939 | class Code2E(SemanticRule): 940 | def execute(self): 941 | self.__rule(self.node) 942 | 943 | def __rule(self, node): 944 | for c in node.children[0].code: 945 | node.code.append(c) 946 | 947 | 948 | class Code2C0(SemanticRule): 949 | def execute(self): 950 | self.__rule(self.node) 951 | 952 | def __rule(self, node): 953 | node.fun = node.parent.fun 954 | 955 | 956 | class Code3E(SemanticRule): 957 | def execute(self): 958 | self.__rule(self.node) 959 | 960 | def __rule(self, node): 961 | for c in node.children[0].code: 962 | node.code.append(c) 963 | 964 | 965 | class Code3C0(SemanticRule): 966 | def execute(self): 967 | self.__rule(self.node) 968 | 969 | def __rule(self, node): 970 | node.fun = node.parent.fun 971 | 972 | 973 | # 17 974 | class NormalStatement0E(SemanticRule): 975 | def execute(self): 976 | self.__rule(self.node) 977 | 978 | def __rule(self, node): 979 | node.code.clear() 980 | 981 | 982 | class NormalStatement1E(SemanticRule): 983 | def execute(self): 984 | self.__rule(self.node) 985 | 986 | def __rule(self, node): 987 | for c in node.children[1].code: 988 | node.code.append(c) 989 | 990 | 991 | class NormalStatement1C1(SemanticRule): 992 | def execute(self): 993 | self.__rule(self.node) 994 | 995 | def __rule(self, node): 996 | node.fun = node.parent.fun 997 | node.id = node.get_pre_brother(1).lexical 998 | 999 | 1000 | # 18 1001 | class NormalStatementFollow0E(SemanticRule): 1002 | def execute(self): 1003 | self.__rule(self.node) 1004 | 1005 | def __rule(self, node): 1006 | if node.children[0].type == 'var': 1007 | for c in node.children[2].code: 1008 | node.code.append(c) 1009 | node.code.append(node.id + ' := ' + node.children[2].name) 1010 | if node.children[0].type == 'array': 1011 | for c in node.children[0].code: 1012 | node.code.append(c) 1013 | for c in node.children[2].code: 1014 | node.code.append(c) 1015 | node.code.append(node.id + '[' + node.children[0].name + ']' + ' := ' + node.children[2].name) 1016 | 1017 | 1018 | class NormalStatementFollow0C0(SemanticRule): 1019 | def execute(self): 1020 | self.__rule(self.node) 1021 | 1022 | def __rule(self, node): 1023 | node.fun = node.parent.fun 1024 | 1025 | 1026 | class NormalStatementFollow0C2(SemanticRule): 1027 | def execute(self): 1028 | self.__rule(self.node) 1029 | 1030 | def __rule(self, node): 1031 | node.fun = node.parent.fun 1032 | 1033 | 1034 | class NormalStatementFollow1E(SemanticRule): 1035 | def execute(self): 1036 | self.__rule(self.node) 1037 | 1038 | def __rule(self, node): 1039 | for c in node.children[0].code: 1040 | node.code.append(c) 1041 | node.code.append('call ' + node.id + ', ' + str(symbol_table_pool.query(node.id).get_params_num())) 1042 | 1043 | 1044 | class NormalStatementFollow1C0(SemanticRule): 1045 | def execute(self): 1046 | self.__rule(self.node) 1047 | 1048 | def __rule(self, node): 1049 | node.fun = node.parent.fun 1050 | node.id = node.parent.id 1051 | 1052 | 1053 | # 19 1054 | class CallFollow0E(SemanticRule): 1055 | def execute(self): 1056 | self.__rule(self.node) 1057 | 1058 | def __rule(self, node): 1059 | for c in node.children[1].code: 1060 | node.code.append(c) 1061 | 1062 | 1063 | class CallFollow0C1(SemanticRule): 1064 | def execute(self): 1065 | self.__rule(self.node) 1066 | 1067 | def __rule(self, node): 1068 | node.fun = node.parent.fun 1069 | node.id = node.parent.id 1070 | 1071 | 1072 | # 20 1073 | class CallParams0E(SemanticRule): 1074 | def execute(self): 1075 | self.__rule(self.node) 1076 | 1077 | def __rule(self, node): 1078 | if symbol_table_pool.query(node.id).get_params_num() != node.children[0].num: 1079 | self.errors.append(SemanticError('函数体' + node.fun + '调用' + node.id + '的时候,参数数量不匹配')) 1080 | else: 1081 | for c in node.children[0].code: 1082 | node.code.append(c) 1083 | 1084 | 1085 | class CallParams0C0(SemanticRule): 1086 | def execute(self): 1087 | self.__rule(self.node) 1088 | 1089 | def __rule(self, node): 1090 | node.fun = node.parent.fun 1091 | 1092 | 1093 | class CallParams1E(SemanticRule): 1094 | def execute(self): 1095 | self.__rule(self.node) 1096 | 1097 | def __rule(self, node): 1098 | if symbol_table_pool.query(node.fun).get_params_num() != 0: 1099 | self.errors.append(SemanticError('函数体' + node.fun + '调用' + node.id + '的时候,参数数量不匹配')) 1100 | 1101 | 1102 | # 21 1103 | class CallParamList0E(SemanticRule): 1104 | def execute(self): 1105 | self.__rule(self.node) 1106 | 1107 | def __rule(self, node): 1108 | node.num = 1 + node.children[1].num 1109 | for c in node.children[0].code: 1110 | node.code.append(c) 1111 | for c in node.children[1].code: 1112 | node.code.append(c) 1113 | node.code.append('param ' + node.children[0].name) 1114 | for name in node.children[1].names: 1115 | node.code.append('param ' + name) 1116 | 1117 | 1118 | class CallParamList0C0(SemanticRule): 1119 | def execute(self): 1120 | self.__rule(self.node) 1121 | 1122 | def __rule(self, node): 1123 | node.fun = node.parent.fun 1124 | 1125 | 1126 | class CallParamList0C1(SemanticRule): 1127 | def execute(self): 1128 | self.__rule(self.node) 1129 | 1130 | def __rule(self, node): 1131 | node.fun = node.parent.fun 1132 | 1133 | 1134 | # 22 1135 | class CallParamFollow0E(SemanticRule): 1136 | def execute(self): 1137 | self.__rule(self.node) 1138 | 1139 | def __rule(self, node): 1140 | node.num = 1 + node.children[2].num 1141 | for c in node.children[1].code: 1142 | node.code.append(c) 1143 | for c in node.children[2].code: 1144 | node.code.append(c) 1145 | node.names.append(node.children[1].name) 1146 | for n in node.children[2].names: 1147 | node.names.append(n) 1148 | 1149 | 1150 | class CallParamFollow0C1(SemanticRule): 1151 | def execute(self): 1152 | self.__rule(self.node) 1153 | 1154 | def __rule(self, node): 1155 | node.fun = node.parent.fun 1156 | 1157 | 1158 | class CallParamFollow0C2(SemanticRule): 1159 | def execute(self): 1160 | self.__rule(self.node) 1161 | 1162 | def __rule(self, node): 1163 | node.fun = node.parent.fun 1164 | 1165 | 1166 | class CallParamFollow1E(SemanticRule): 1167 | def execute(self): 1168 | self.__rule(self.node) 1169 | 1170 | def __rule(self, node): 1171 | node.num = 0 1172 | node.code.clear() 1173 | node.names.clear() 1174 | 1175 | 1176 | # 23 1177 | class SelectionStatement0E(SemanticRule): 1178 | def execute(self): 1179 | self.__rule(self.node) 1180 | 1181 | def __rule(self, node): 1182 | if not node.children[2].bool: 1183 | self.errors.append(SemanticError('if-结构中的表达式不是bool表达式')) 1184 | else: 1185 | for c in node.children[2].code: 1186 | node.code.append(c) 1187 | if_block = get_temp_block_name() 1188 | else_block = get_temp_block_name() 1189 | next_block = get_temp_block_name() 1190 | node.code.append('if ' + node.children[2].name + ' goto ' + if_block) 1191 | node.code.append(else_block + ':') 1192 | for c in node.children[7].code: 1193 | node.code.append(c) 1194 | node.code.append('goto ' + next_block) 1195 | node.code.append(if_block + ':') 1196 | for c in node.children[5].code: 1197 | node.code.append(c) 1198 | node.code.append('goto ' + next_block) 1199 | node.code.append(next_block + ':') 1200 | 1201 | 1202 | class SelectionStatement0C2(SemanticRule): 1203 | def execute(self): 1204 | self.__rule(self.node) 1205 | 1206 | def __rule(self, node): 1207 | node.fun = node.parent.fun 1208 | 1209 | 1210 | class SelectionStatement0C5(SemanticRule): 1211 | def execute(self): 1212 | self.__rule(self.node) 1213 | 1214 | def __rule(self, node): 1215 | node.fun = node.parent.fun 1216 | 1217 | 1218 | class SelectionStatement0C7(SemanticRule): 1219 | def execute(self): 1220 | self.__rule(self.node) 1221 | 1222 | def __rule(self, node): 1223 | node.fun = node.parent.fun 1224 | 1225 | 1226 | # 24 1227 | class SelectionFollow0E(SemanticRule): 1228 | def execute(self): 1229 | self.__rule(self.node) 1230 | 1231 | def __rule(self, node): 1232 | for c in node.children[2].code: 1233 | node.code.append(c) 1234 | 1235 | 1236 | class SelectionFollow0C2(SemanticRule): 1237 | def execute(self): 1238 | self.__rule(self.node) 1239 | 1240 | def __rule(self, node): 1241 | node.fun = node.parent.fun 1242 | 1243 | 1244 | class SelectionFollow1E(SemanticRule): 1245 | def execute(self): 1246 | self.__rule(self.node) 1247 | 1248 | def __rule(self, node): 1249 | node.code.clear() 1250 | 1251 | 1252 | # 25 1253 | class IterationStatement0E(SemanticRule): 1254 | def execute(self): 1255 | self.__rule(self.node) 1256 | 1257 | def __rule(self, node): 1258 | judge_block = get_temp_block_name() 1259 | iteration_block = get_temp_block_name() 1260 | next_block = get_temp_block_name() 1261 | node.code.append(judge_block + ':') 1262 | for c in node.children[2].code: 1263 | node.code.append(c) 1264 | node.code.append('if ' + node.children[2].name + ' goto ' + iteration_block) 1265 | node.code.append('goto ' + next_block) 1266 | node.code.append(iteration_block + ':') 1267 | for c in node.children[4].code: 1268 | node.code.append(c) 1269 | node.code.append('goto ' + judge_block) 1270 | node.code.append(next_block + ':') 1271 | 1272 | 1273 | class IterationStatement0C2(SemanticRule): 1274 | def execute(self): 1275 | self.__rule(self.node) 1276 | 1277 | def __rule(self, node): 1278 | node.fun = node.parent.fun 1279 | 1280 | 1281 | class IterationStatement0C4(SemanticRule): 1282 | def execute(self): 1283 | self.__rule(self.node) 1284 | 1285 | def __rule(self, node): 1286 | node.fun = node.parent.fun 1287 | 1288 | 1289 | # 26 1290 | class IterationFollow0E(SemanticRule): 1291 | def execute(self): 1292 | self.__rule(self.node) 1293 | 1294 | def __rule(self, node): 1295 | for c in node.children[1].code: 1296 | node.code.append(c) 1297 | 1298 | 1299 | class IterationFollow0C1(SemanticRule): 1300 | def execute(self): 1301 | self.__rule(self.node) 1302 | 1303 | def __rule(self, node): 1304 | node.fun = node.parent.fun 1305 | 1306 | 1307 | class IterationFollow1E(SemanticRule): 1308 | def execute(self): 1309 | self.__rule(self.node) 1310 | 1311 | def __rule(self, node): 1312 | for c in node.children[0].code: 1313 | node.code.append(c) 1314 | 1315 | 1316 | class IterationFollow1C0(SemanticRule): 1317 | def execute(self): 1318 | self.__rule(self.node) 1319 | 1320 | def __rule(self, node): 1321 | node.fun = node.parent.fun 1322 | 1323 | 1324 | # 27 1325 | class ReturnStatement0E(SemanticRule): 1326 | def execute(self): 1327 | self.__rule(self.node) 1328 | 1329 | def __rule(self, node): 1330 | for c in node.children[1].code: 1331 | node.code.append(c) 1332 | 1333 | 1334 | class ReturnStatement0C1(SemanticRule): 1335 | def execute(self): 1336 | self.__rule(self.node) 1337 | 1338 | def __rule(self, node): 1339 | node.fun = node.parent.fun 1340 | 1341 | 1342 | # 28 1343 | class ReturnFollow0E(SemanticRule): 1344 | def execute(self): 1345 | self.__rule(self.node) 1346 | 1347 | def __rule(self, node): 1348 | node.code.append('return') 1349 | 1350 | 1351 | class ReturnFollow1E(SemanticRule): 1352 | def execute(self): 1353 | self.__rule(self.node) 1354 | 1355 | def __rule(self, node): 1356 | for c in node.children[0].code: 1357 | node.code.append(c) 1358 | node.code.append('return ' + node.children[0].name) 1359 | 1360 | 1361 | class ReturnFollow1C0(SemanticRule): 1362 | def execute(self): 1363 | self.__rule(self.node) 1364 | 1365 | def __rule(self, node): 1366 | node.fun = node.parent.fun 1367 | 1368 | 1369 | # 29 1370 | class VarFollow0E(SemanticRule): 1371 | def execute(self): 1372 | self.__rule(self.node) 1373 | 1374 | def __rule(self, node): 1375 | node.type = 'array' 1376 | node.name = node.children[1].name 1377 | for c in node.children[1].code: 1378 | node.code.append(c) 1379 | 1380 | 1381 | class VarFollow0C1(SemanticRule): 1382 | def execute(self): 1383 | self.__rule(self.node) 1384 | 1385 | def __rule(self, node): 1386 | node.fun = node.parent.fun 1387 | 1388 | 1389 | class VarFollow1E(SemanticRule): 1390 | def execute(self): 1391 | self.__rule(self.node) 1392 | 1393 | def __rule(self, node): 1394 | node.type = 'var' 1395 | 1396 | 1397 | # 30 1398 | class Expression0E(SemanticRule): 1399 | def execute(self): 1400 | self.__rule(self.node) 1401 | 1402 | def __rule(self, node): 1403 | node.bool = node.children[1].bool 1404 | if node.children[1].bool: 1405 | node.name = get_temp_var_name() 1406 | for c in node.children[0].code: 1407 | node.code.append(c) 1408 | for c in node.children[1].code: 1409 | node.code.append(c) 1410 | node.code.append(node.name + ' := ' + node.children[0].name + ' ' 1411 | + node.children[1].op + ' ' + node.children[1].name) 1412 | else: 1413 | node.name = node.children[0].name 1414 | for c in node.children[0].code: 1415 | node.code.append(c) 1416 | 1417 | 1418 | class Expression0C0(SemanticRule): 1419 | def execute(self): 1420 | self.__rule(self.node) 1421 | 1422 | def __rule(self, node): 1423 | node.fun = node.parent.fun 1424 | 1425 | 1426 | class Expression0C1(SemanticRule): 1427 | def execute(self): 1428 | self.__rule(self.node) 1429 | 1430 | def __rule(self, node): 1431 | node.fun = node.parent.fun 1432 | 1433 | 1434 | # 31 1435 | class ExpressionFollow0E(SemanticRule): 1436 | def execute(self): 1437 | self.__rule(self.node) 1438 | 1439 | def __rule(self, node): 1440 | node.bool = True 1441 | node.op = node.children[0].op 1442 | node.name = node.children[1].name 1443 | for c in node.children[1].code: 1444 | node.code.append(c) 1445 | 1446 | 1447 | class ExpressionFollow0C1(SemanticRule): 1448 | def execute(self): 1449 | self.__rule(self.node) 1450 | 1451 | def __rule(self, node): 1452 | node.fun = node.parent.fun 1453 | 1454 | 1455 | class ExpressionFollow1E(SemanticRule): 1456 | def execute(self): 1457 | self.__rule(self.node) 1458 | 1459 | def __rule(self, node): 1460 | node.bool = False 1461 | 1462 | 1463 | # 32 1464 | class RelOp0E(SemanticRule): 1465 | def execute(self): 1466 | self.__rule(self.node) 1467 | 1468 | def __rule(self, node): 1469 | node.op = node.children[0].lexical 1470 | 1471 | 1472 | class RelOp1E(SemanticRule): 1473 | def execute(self): 1474 | self.__rule(self.node) 1475 | 1476 | def __rule(self, node): 1477 | node.op = node.children[0].lexical 1478 | 1479 | 1480 | class RelOp2E(SemanticRule): 1481 | def execute(self): 1482 | self.__rule(self.node) 1483 | 1484 | def __rule(self, node): 1485 | node.op = node.children[0].lexical 1486 | 1487 | 1488 | class RelOp3E(SemanticRule): 1489 | def execute(self): 1490 | self.__rule(self.node) 1491 | 1492 | def __rule(self, node): 1493 | node.op = node.children[0].lexical 1494 | 1495 | 1496 | class RelOp4E(SemanticRule): 1497 | def execute(self): 1498 | self.__rule(self.node) 1499 | 1500 | def __rule(self, node): 1501 | node.op = node.children[0].lexical 1502 | 1503 | 1504 | class RelOp5E(SemanticRule): 1505 | def execute(self): 1506 | self.__rule(self.node) 1507 | 1508 | def __rule(self, node): 1509 | node.op = node.children[0].lexical 1510 | 1511 | 1512 | # 33 1513 | class AdditiveExpr0E(SemanticRule): 1514 | def execute(self): 1515 | self.__rule(self.node) 1516 | 1517 | def __rule(self, node): 1518 | if node.children[1].add: 1519 | node.name = get_temp_var_name() 1520 | for c in node.children[0].code: 1521 | node.code.append(c) 1522 | for c in node.children[1].code: 1523 | node.code.append(c) 1524 | node.code.append(node.name + ' := ' + node.children[0].name + ' ' + node.children[1].op 1525 | + ' ' + node.children[1].name) 1526 | else: 1527 | node.name = node.children[0].name 1528 | for c in node.children[0].code: 1529 | node.code.append(c) 1530 | 1531 | 1532 | class AdditiveExpr0C0(SemanticRule): 1533 | def execute(self): 1534 | self.__rule(self.node) 1535 | 1536 | def __rule(self, node): 1537 | node.fun = node.parent.fun 1538 | 1539 | 1540 | class AdditiveExpr0C1(SemanticRule): 1541 | def execute(self): 1542 | self.__rule(self.node) 1543 | 1544 | def __rule(self, node): 1545 | node.fun = node.parent.fun 1546 | 1547 | 1548 | # 34 1549 | class AdditiveExprFollow0E(SemanticRule): 1550 | def execute(self): 1551 | self.__rule(self.node) 1552 | 1553 | def __rule(self, node): 1554 | node.add = True 1555 | node.op = node.children[0].op 1556 | if node.children[2].add: 1557 | node.name = get_temp_var_name() 1558 | for c in node.children[1].code: 1559 | node.code.append(c) 1560 | for c in node.children[2].code: 1561 | node.code.append(c) 1562 | node.code.append(node.name + ' := ' + node.children[1].name + ' ' + node.children[2].op 1563 | + ' ' + node.children[2].name) 1564 | else: 1565 | node.name = node.children[1].name 1566 | for c in node.children[1].code: 1567 | node.code.append(c) 1568 | 1569 | 1570 | class AdditiveExprFollow0C1(SemanticRule): 1571 | def execute(self): 1572 | self.__rule(self.node) 1573 | 1574 | def __rule(self, node): 1575 | node.fun = node.parent.fun 1576 | 1577 | 1578 | class AdditiveExprFollow0C2(SemanticRule): 1579 | def execute(self): 1580 | self.__rule(self.node) 1581 | 1582 | def __rule(self, node): 1583 | node.fun = node.parent.fun 1584 | 1585 | 1586 | class AdditiveExprFollow1E(SemanticRule): 1587 | def execute(self): 1588 | self.__rule(self.node) 1589 | 1590 | def __rule(self, node): 1591 | node.add = False 1592 | 1593 | 1594 | # 35 1595 | class AddOp0E(SemanticRule): 1596 | def execute(self): 1597 | self.__rule(self.node) 1598 | 1599 | def __rule(self, node): 1600 | node.op = node.children[0].lexical 1601 | 1602 | 1603 | class AddOp1E(SemanticRule): 1604 | def execute(self): 1605 | self.__rule(self.node) 1606 | 1607 | def __rule(self, node): 1608 | node.op = node.children[0].lexical 1609 | 1610 | 1611 | # 36 1612 | class Term0E(SemanticRule): 1613 | def execute(self): 1614 | self.__rule(self.node) 1615 | 1616 | def __rule(self, node): 1617 | if node.children[1].mul: 1618 | node.name = get_temp_var_name() 1619 | for c in node.children[0].code: 1620 | node.code.append(c) 1621 | for c in node.children[1].code: 1622 | node.code.append(c) 1623 | node.code.append(node.name + ' := ' + node.children[0].name + ' ' + node.children[1].op 1624 | + ' ' + node.children[1].name) 1625 | else: 1626 | node.name = node.children[0].name 1627 | for c in node.children[0].code: 1628 | node.code.append(c) 1629 | 1630 | 1631 | class Term0C0(SemanticRule): 1632 | def execute(self): 1633 | self.__rule(self.node) 1634 | 1635 | def __rule(self, node): 1636 | node.fun = node.parent.fun 1637 | 1638 | 1639 | class Term0C1(SemanticRule): 1640 | def execute(self): 1641 | self.__rule(self.node) 1642 | 1643 | def __rule(self, node): 1644 | node.fun = node.parent.fun 1645 | 1646 | 1647 | # 37 1648 | class TermFollow0E(SemanticRule): 1649 | def execute(self): 1650 | self.__rule(self.node) 1651 | 1652 | def __rule(self, node): 1653 | node.mul = True 1654 | node.op = node.children[0].op 1655 | if node.children[2].mul: 1656 | node.name = get_temp_var_name() 1657 | for c in node.children[1].code: 1658 | node.code.append(c) 1659 | for c in node.children[2].code: 1660 | node.code.append(c) 1661 | node.code.append(node.name + ' := ' + node.children[1].name + ' ' + node.children[2].op 1662 | + ' ' + node.children[2].name) 1663 | else: 1664 | node.name = node.children[1].name 1665 | for c in node.children[1].code: 1666 | node.code.append(c) 1667 | 1668 | 1669 | class TermFollow0C1(SemanticRule): 1670 | def execute(self): 1671 | self.__rule(self.node) 1672 | 1673 | def __rule(self, node): 1674 | node.fun = node.parent.fun 1675 | 1676 | 1677 | class TermFollow0C2(SemanticRule): 1678 | def execute(self): 1679 | self.__rule(self.node) 1680 | 1681 | def __rule(self, node): 1682 | node.fun = node.parent.fun 1683 | 1684 | 1685 | # 38 1686 | class MulOp0E(SemanticRule): 1687 | def execute(self): 1688 | self.__rule(self.node) 1689 | 1690 | def __rule(self, node): 1691 | node.op = node.children[0].lexical 1692 | 1693 | 1694 | class MulOp1E(SemanticRule): 1695 | def execute(self): 1696 | self.__rule(self.node) 1697 | 1698 | def __rule(self, node): 1699 | node.op = node.children[0].lexical 1700 | 1701 | 1702 | # 39 1703 | class Factor0E(SemanticRule): 1704 | def execute(self): 1705 | self.__rule(self.node) 1706 | 1707 | def __rule(self, node): 1708 | for c in node.children[1].code: 1709 | node.code.append(c) 1710 | node.name = node.children[1].name 1711 | 1712 | 1713 | class Factor0C1(SemanticRule): 1714 | def execute(self): 1715 | self.__rule(self.node) 1716 | 1717 | def __rule(self, node): 1718 | node.fun = node.parent.fun 1719 | 1720 | 1721 | class Factor1E(SemanticRule): 1722 | def execute(self): 1723 | self.__rule(self.node) 1724 | 1725 | def __rule(self, node): 1726 | for c in node.children[1].code: 1727 | node.code.append(c) 1728 | node.name = node.children[1].name 1729 | 1730 | 1731 | class Factor1C1(SemanticRule): 1732 | def execute(self): 1733 | self.__rule(self.node) 1734 | 1735 | def __rule(self, node): 1736 | node.id = node.get_pre_brother(1).lexical 1737 | node.fun = node.parent.fun 1738 | 1739 | 1740 | class Factor2E(SemanticRule): 1741 | def execute(self): 1742 | self.__rule(self.node) 1743 | 1744 | def __rule(self, node): 1745 | node.name = get_temp_var_name() 1746 | node.code.append(node.name + ' := ' + node.children[0].lexical) 1747 | 1748 | 1749 | # 40 1750 | class IdFactorFollow0E(SemanticRule): 1751 | def execute(self): 1752 | self.__rule(self.node) 1753 | 1754 | def __rule(self, node): 1755 | if symbol_table_pool.query(node.fun).exist(node.id): 1756 | if node.children[0].type == 'var': 1757 | node.name = node.id 1758 | if node.children[0].type == 'array': 1759 | node.name = get_temp_var_name() 1760 | for c in node.children[0].code: 1761 | node.code.append(c) 1762 | node.code.append(node.name + ' := ' + node.id + '[' + node.children[0].name + ']') 1763 | else: 1764 | self.errors.append('变量' + node.id + '未定义') 1765 | 1766 | 1767 | class IdFactorFollow1E(SemanticRule): 1768 | def execute(self): 1769 | self.__rule(self.node) 1770 | 1771 | def __rule(self, node): 1772 | if symbol_table_pool.fun_table.exist(node.id): 1773 | if node.children[1].num != symbol_table_pool.query(node.id).get_params_num(): 1774 | self.errors.append('调用函数' + node.id + '的时候参数数量不匹配') 1775 | else: 1776 | for c in node.children[1].code: 1777 | node.code.append(c) 1778 | node.code.append('call ' + node.id + ', ' + str(symbol_table_pool.query(node.fun).get_params_num())) 1779 | node.name = get_temp_var_name() 1780 | node.code.append(node.name + ' := ' + 'result') 1781 | else: 1782 | self.errors.append('函数' + node.id + '未定义') 1783 | 1784 | 1785 | class IdFactorFollow1C1(SemanticRule): 1786 | def execute(self): 1787 | self.__rule(self.node) 1788 | 1789 | def __rule(self, node): 1790 | node.fun = node.parent.fun 1791 | 1792 | 1793 | # 41 1794 | class Args0E(SemanticRule): 1795 | def execute(self): 1796 | self.__rule(self.node) 1797 | 1798 | def __rule(self, node): 1799 | for c in node.children[0].code: 1800 | node.code.append(c) 1801 | node.num = node.children[0].num 1802 | 1803 | 1804 | class Args0C0(SemanticRule): 1805 | def execute(self): 1806 | self.__rule(self.node) 1807 | 1808 | def __rule(self, node): 1809 | node.fun = node.parent.fun 1810 | 1811 | 1812 | class Args1E(SemanticRule): 1813 | def execute(self): 1814 | self.__rule(self.node) 1815 | 1816 | def __rule(self, node): 1817 | node.code.clear() 1818 | node.num = 0 1819 | 1820 | 1821 | # 42 1822 | class ArgList0E(SemanticRule): 1823 | def execute(self): 1824 | self.__rule(self.node) 1825 | 1826 | def __rule(self, node): 1827 | node.num = 1 + node.children[1].num 1828 | for c in node.children[0].code: 1829 | node.code.append(c) 1830 | for c in node.children[1].code: 1831 | node.code.append(c) 1832 | node.code.append('param ' + node.children[0].name) 1833 | for name in node.children[1].names: 1834 | node.code.append('param ' + name) 1835 | 1836 | 1837 | class ArgList0C0(SemanticRule): 1838 | def execute(self): 1839 | self.__rule(self.node) 1840 | 1841 | def __rule(self, node): 1842 | node.fun = node.parent.fun 1843 | 1844 | 1845 | class ArgList0C1(SemanticRule): 1846 | def execute(self): 1847 | self.__rule(self.node) 1848 | 1849 | def __rule(self, node): 1850 | node.fun = node.parent.fun 1851 | 1852 | 1853 | # 43 1854 | class ArgListFollow0E(SemanticRule): 1855 | def execute(self): 1856 | self.__rule(self.node) 1857 | 1858 | def __rule(self, node): 1859 | node.num = 1 + node.children[2].num 1860 | for c in node.children[1].code: 1861 | node.code.append(c) 1862 | for c in node.children[2].code: 1863 | node.code.append(c) 1864 | node.names.append(node.children[1].name) 1865 | for name in node.children[2].names: 1866 | node.names.append(name) 1867 | 1868 | 1869 | class ArgListFollow0C1(SemanticRule): 1870 | def execute(self): 1871 | self.__rule(self.node) 1872 | 1873 | def __rule(self, node): 1874 | node.fun = node.parent.fun 1875 | 1876 | 1877 | class ArgListFollow0C2(SemanticRule): 1878 | def execute(self): 1879 | self.__rule(self.node) 1880 | 1881 | def __rule(self, node): 1882 | node.fun = node.parent.fun 1883 | 1884 | 1885 | class ArgListFollow1E(SemanticRule): 1886 | def execute(self): 1887 | self.__rule(self.node) 1888 | 1889 | def __rule(self, node): 1890 | node.num = 0 1891 | node.code.clear() 1892 | node.names.clear() 1893 | -------------------------------------------------------------------------------- /semantic/symbol.py: -------------------------------------------------------------------------------- 1 | class Symbol: 2 | """ 3 | 符号基类 4 | """ 5 | def __init__(self, name): 6 | """ 7 | 构造 8 | :param name: 符号名 9 | """ 10 | self.name = name 11 | 12 | 13 | class SymbolTable: 14 | """ 15 | 符号表 16 | """ 17 | def __init__(self): 18 | """ 19 | 构造 20 | """ 21 | self._table = list() 22 | 23 | def exist(self, name): 24 | """ 25 | 给定名字的符号是否存在 26 | :param name: 27 | :return: True/False 28 | """ 29 | for s in self._table: 30 | if s.name == name: 31 | return True 32 | return False 33 | 34 | def query(self, name): 35 | """ 36 | 查询特定名字的符号 37 | :param name: 名字 38 | :return: 符号 39 | """ 40 | for symbol in self._table: 41 | if symbol.name == name: 42 | return symbol 43 | return None 44 | 45 | def append(self, symbol): 46 | """ 47 | 填入符号 48 | :param symbol: 符号 49 | """ 50 | pass 51 | 52 | def num(self): 53 | """ 54 | 获取符号总数 55 | :return: 符号总数 56 | """ 57 | return len(self._table) 58 | 59 | def get(self, index): 60 | """ 61 | 根据索引来获取符号 62 | :param index: 索引 63 | :return: 符号 64 | """ 65 | return self._table[index] 66 | 67 | 68 | class SymbolTablePool: 69 | """ 70 | 符号表池 71 | """ 72 | def __init__(self): 73 | """ 74 | 构造 75 | """ 76 | self.global_var_table = None 77 | self.local_var_tables = None 78 | self.fun_table = None 79 | 80 | def init(self): 81 | """ 82 | 初始化符号表池 83 | """ 84 | self.global_var_table = GlobalVarTable() 85 | self.local_var_tables = list() 86 | self.fun_table = FunTable() 87 | 88 | # 添加 output 和 input 的支持 89 | self.local_var_tables.append( 90 | LocalVarTable('input', self.global_var_table) 91 | ) 92 | self.local_var_tables.append( 93 | LocalVarTable('output', self.global_var_table) 94 | ) 95 | self.query('output').append( 96 | LocalVar('num', 'int', 4, True) 97 | ) 98 | self.fun_table.append( 99 | Fun('input', 'int', self.query('input')) 100 | ) 101 | self.fun_table.append( 102 | Fun('output', 'void', self.query('output')) 103 | ) 104 | 105 | def query(self, local_var_table_name): 106 | """ 107 | 查询局部变量表 108 | :param local_var_table_name: 表名 109 | :return: 局部变量表 110 | """ 111 | for table in self.local_var_tables: 112 | if table.name == local_var_table_name: 113 | return table 114 | return None 115 | 116 | def append(self, local_var_table): 117 | """ 118 | 添加一张局部变量表 119 | :param local_var_table: 局部变量表 120 | """ 121 | self.local_var_tables.append(local_var_table) 122 | 123 | 124 | class GlobalVarTable(SymbolTable): 125 | """ 126 | 全局变量表 127 | """ 128 | def __init__(self): 129 | """ 130 | 构造 131 | :param name: 132 | """ 133 | super().__init__() 134 | self.__width = 0 135 | 136 | def append(self, symbol): 137 | """ 138 | 添加符号 139 | :param symbol: 符号 140 | """ 141 | self._table.append(symbol) 142 | self._table[-1].offset = self.__width 143 | self.__width += self._table[-1].width 144 | 145 | 146 | class GlobalVar(Symbol): 147 | """ 148 | 全局变量 149 | """ 150 | def __init__(self, g_name, g_type, g_width): 151 | """ 152 | 全局变量 153 | :param g_name: 名字 154 | :param g_type: 类型 155 | :param g_width: 长度 156 | """ 157 | super().__init__(g_name) 158 | self.type = g_type 159 | self.width = g_width 160 | 161 | 162 | class LocalVarTable(SymbolTable): 163 | """ 164 | 局部变量表 165 | """ 166 | def __init__(self, name, global_var_table): 167 | """ 168 | 构造 169 | :param name: 表名 170 | :param global_var_table 全局变量表 171 | """ 172 | super().__init__() 173 | self.name = name 174 | self.outer = global_var_table 175 | self.__width = 0 176 | 177 | def append(self, symbol): 178 | """ 179 | 填入新符号 180 | :param symbol: 181 | """ 182 | self._table.append(symbol) 183 | self._table[-1].offset = self.__width 184 | self.__width += self._table[-1].offset 185 | 186 | def exist(self, name): 187 | """ 188 | 是否已经存在 189 | :param name: 符号名 190 | :return: True/False 191 | """ 192 | if self.outer.exist(name): 193 | return True 194 | else: 195 | for symbol in self._table: 196 | if symbol.name == name: 197 | return True 198 | return False 199 | 200 | def get_params_num(self): 201 | """ 202 | 获取参数个数 203 | :return: 参数个数 204 | """ 205 | num = 0 206 | for symbol in self._table: 207 | if symbol.is_param: 208 | num += 1 209 | return num 210 | 211 | def get_params(self): 212 | """ 213 | 获取参数列表 214 | :return: 参数列表 215 | """ 216 | params = list() 217 | for symbol in self._table: 218 | if symbol.is_param: 219 | params.append(symbol) 220 | return params 221 | 222 | 223 | class LocalVar(Symbol): 224 | """ 225 | 局部变量 226 | """ 227 | def __init__(self, l_name, l_type, l_width, l_is_param): 228 | """ 229 | 构造 230 | :param l_name: 名字 231 | :param l_type: 类型 232 | :param l_width: 占空间 233 | :param l_is_param: 是否为参数 234 | """ 235 | super().__init__(l_name) 236 | self.type = l_type 237 | self.width = l_width 238 | self.is_param = l_is_param 239 | 240 | 241 | class FunTable(SymbolTable): 242 | """ 243 | 函数表 244 | """ 245 | def __init__(self): 246 | """ 247 | 构造 248 | """ 249 | super().__init__() 250 | 251 | def append(self, symbol): 252 | """ 253 | 填入一个新的函数 254 | :param symbol: 函数 255 | """ 256 | self._table.append(symbol) 257 | 258 | 259 | class Fun(Symbol): 260 | """ 261 | 函数 262 | """ 263 | def __init__(self, name, return_type, local_var_table): 264 | """ 265 | 构造 266 | :param name: 函数名 267 | :param return_type: 返回类型 268 | :param local_var_table: 对应的局部变量表 269 | """ 270 | super().__init__(name) 271 | self.param_types = list() 272 | self.return_type = return_type 273 | self.table = local_var_table 274 | -------------------------------------------------------------------------------- /syntax/rule.py: -------------------------------------------------------------------------------- 1 | class Sign: 2 | """ 3 | 符号 4 | """ 5 | def __init__(self, sign_type, sign_str='', sign_line=-1): 6 | """ 7 | 构造 8 | :param sign_type: 符号的类型 9 | :param sign_str: 符号的内容(可以为空) 10 | :param sign_line: 符号所在行数(可以为空) 11 | """ 12 | self.type = sign_type 13 | self.str = sign_str 14 | self.line = sign_line 15 | 16 | def is_terminal_sign(self): 17 | """ 18 | 是不是终结符 19 | :return: True/False 20 | """ 21 | if self.type == 'empty': 22 | return True 23 | else: 24 | for i in terminal_sign_type: 25 | if i == self.type: 26 | return True 27 | return False 28 | 29 | def is_non_terminal_sign(self): 30 | """ 31 | 是不是非终结符 32 | :return: True/False 33 | """ 34 | for i in non_terminal_sign_type: 35 | if i == self.type: 36 | return True 37 | return False 38 | 39 | def is_empty_sign(self): 40 | """ 41 | 是不是空字 42 | :return: True/False 43 | """ 44 | return self.type == 'empty' 45 | 46 | 47 | class Production: 48 | """ 49 | 产生式 50 | """ 51 | def __init__(self, left_type, right_types, semantic_start, semantic_children, semantic_end): 52 | """ 53 | 产生式左边 54 | :param left_type: 产生式左边的符号类型 55 | :param right_types: 产生式右边的符号类型列表 56 | :param semantic_start: 语义操作关键字 - 开始 57 | :param semantic_children: 语义操作关键字 - 孩子 58 | :param semantic_end: 语义操作关键字 - 结束 59 | """ 60 | self.left = Sign(left_type) 61 | self.right = list() 62 | for i in right_types: 63 | self.right.append(Sign(i)) 64 | 65 | # 调试用的 66 | self.str = self.left.type + ' ->' 67 | for i in self.right: 68 | self.str += ' ' + i.type 69 | 70 | # 语义操作关键字 71 | self.semantic_start = semantic_start 72 | self.semantic_children = list() 73 | for c in semantic_children: 74 | self.semantic_children.append(c) 75 | self.semantic_end = semantic_end 76 | 77 | 78 | """ 79 | 1. program -> define-list 80 | 2. define-list -> define define-list 81 | | empty 82 | 3. define -> type ID define-type 83 | 4. define-type -> var-define-follow 84 | | fun-define-follow 85 | 5. var-define-follow -> ; 86 | | [ NUM ] ; 87 | 6. type -> int 88 | | void 89 | 7. fun-define-follow -> ( params ) code-block 90 | 8. params -> param-list 91 | | empty 92 | 9. param-list -> param param-follow 93 | 10. param-follow -> , param param-follow 94 | | empty 95 | 11. param -> type ID array-subscript 96 | 12. array-subscript -> [ ] 97 | | empty 98 | 13. code-block -> { local-define-list code-list } 99 | 14. local-define-list -> local-var-define local-define-list 100 | | empty 101 | 15. local-var-define -> type ID var-define-follow 102 | 16. code-list -> code code-list 103 | | empty 104 | 17. code -> normal-statement 105 | | selection-statement 106 | | iteration-statement 107 | | return-statement 108 | 18. normal-statement -> ; 109 | | ID normal-statement-follow 110 | 19. normal-statement-follow -> var-follow = expression ; 111 | | call-follow ; 112 | 20. call-follow -> ( call-params ) 113 | 21. call-params -> call-param-list 114 | | empty 115 | 22. call-param-list -> expression call-param-follow 116 | 23. call-param-follow -> , expression call-param-follow 117 | | empty 118 | 24. selection-statement -> if ( expression ) { code-list } selection-follow 119 | 25. selection-follow -> else { code-list } 120 | | empty 121 | 26. iteration-statement -> while ( expression ) iteration-follow 122 | 27. iteration-follow -> { code-list } 123 | | code 124 | 28. return-statement -> return return-follow 125 | 29. return-follow -> ; 126 | | expression ; 127 | 30. var-follow -> [ expression ] 128 | | empty 129 | 31. expression -> additive-expr expression-follow 130 | 32. expression-follow -> rel-op additive-expr 131 | | empty 132 | 33. rel-op -> <= 133 | | < 134 | | > 135 | | >= 136 | | == 137 | | != 138 | 34. additive-expr -> term additive-expr-follow 139 | 35. additive-expr-follow -> add-op term additive-expr-follow 140 | | empty 141 | 36. add-op -> + 142 | | - 143 | 37. term -> factor term-follow 144 | 38. term-follow -> mul-op factor term-follow 145 | | empty 146 | 39. mul-op -> * 147 | | / 148 | 40. factor -> ( expression ) 149 | | ID id-factor-follow | NUM 150 | 41. id-factor-follow -> var-follow 151 | | ( args ) 152 | 42. args -> arg-list 153 | | empty 154 | 43. arg-list -> expression arg-list-follow 155 | 44. arg-list-follow -> , expression arg-list-follow 156 | | empty 157 | """ 158 | 159 | 160 | # 所有终结符的类型 161 | terminal_sign_type = [ 162 | 'else', 163 | 'if', 164 | 'int', 165 | 'return', 166 | 'void', 167 | 'while', 168 | 'addition', 169 | 'subtraction', 170 | 'multiplication', 171 | 'division', 172 | 'bigger', 173 | 'bigger-equal', 174 | 'smaller', 175 | 'smaller-equal', 176 | 'equal', 177 | 'not-equal', 178 | 'evaluate', 179 | 'semicolon', 180 | 'comma', 181 | 'left-parentheses', 182 | 'right-parentheses', 183 | 'left-bracket', 184 | 'right-bracket', 185 | 'left-brace', 186 | 'right-brace', 187 | 'id', 188 | 'num', 189 | # 在这之前添加非终结符类型,请务必不要动 'pound' 190 | 'pound' 191 | ] 192 | 193 | # 所有非终结符的类型 194 | non_terminal_sign_type = [ 195 | 'program', 196 | 'define-list', 197 | 'define', 198 | 'define-type', 199 | 'var-define-follow', 200 | 'type', 201 | 'fun-define-follow', 202 | 'params', 203 | 'param-list', 204 | 'param-follow', 205 | 'param', 206 | 'array-subscript', 207 | 'code-block', 208 | 'local-define-list', 209 | 'local-var-define', 210 | 'code-list', 211 | 'code', 212 | 'normal-statement', 213 | 'normal-statement-follow', 214 | 'call-follow', 215 | 'call-params', 216 | 'call-param-list', 217 | 'call-param-follow', 218 | 'selection-statement', 219 | 'selection-follow', 220 | 'iteration-statement', 221 | 'iteration-follow', 222 | 'return-statement', 223 | 'return-follow', 224 | # 'eval-statement', 225 | # 'var', 226 | 'var-follow', 227 | 'expression', 228 | 'expression-follow', 229 | 'rel-op', 230 | 'additive-expr', 231 | 'additive-expr-follow', 232 | 'add-op', 233 | 'term', 234 | 'term-follow', 235 | 'mul-op', 236 | 'factor', 237 | 'id-factor-follow', 238 | 'args', 239 | 'arg-list', 240 | 'arg-list-follow' 241 | ] 242 | 243 | # 文法产生式 244 | productions = [ 245 | # 0 246 | Production('program', ['define-list'], 247 | 'Program0S', [None], 'Program0E'), 248 | # 1 249 | Production('define-list', ['define', 'define-list'], 250 | None, [None, None], 'DefineList0E'), 251 | Production('define-list', [], 252 | None, [], 'DefineList1E'), 253 | # 2 254 | Production('define', ['type', 'id', 'define-type'], 255 | None, [None, None, 'Define0C2'], 'Define0E'), 256 | # 3 257 | Production('define-type', ['var-define-follow'], 258 | 'DefineType0S', ['DefineType0C0'], 'DefineType0E'), 259 | Production('define-type', ['fun-define-follow'], 260 | 'DefineType1S', ['DefineType1C0'], 'DefineType1E'), 261 | # 4 262 | Production('var-define-follow', ['semicolon'], 263 | None, [None], 'VarDefineFollow0E'), 264 | Production('var-define-follow', ['left-bracket', 'num', 'right-bracket', 'semicolon'], 265 | None, [None, None, None, None], 'VarDefineFollow1E'), 266 | # 5 267 | Production('type', ['int'], 268 | 'Type0S', [None], None), 269 | Production('type', ['void'], 270 | 'Type1S', [None], None), 271 | # 6 272 | Production('fun-define-follow', ['left-parentheses', 'params', 'right-parentheses', 'code-block'], 273 | None, [None, 'FunDefineFollow0C1', None, 'FunDefineFollow0C3'], 'FunDefineFollow0E'), 274 | # 7 275 | Production('params', ['param-list'], 276 | 'Params0S', ['Params0C0'], None), 277 | Production('params', [], 278 | 'Params1S', [], None), 279 | # 8 280 | Production('param-list', ['param', 'param-follow'], 281 | None, ['ParamList0C0', 'ParamList0C1'], None), 282 | # 9 283 | Production('param-follow', ['comma', 'param', 'param-follow'], 284 | None, [None, 'ParamFollow0C1', 'ParamFollow0C2'], None), 285 | Production('param-follow', [], 286 | None, [], None), 287 | # 10 288 | Production('param', ['type', 'id', 'array-subscript'], 289 | None, [None, None, None], 'Param0E'), 290 | # 11 291 | Production('array-subscript', ['left-bracket', 'right-bracket'], 292 | 'ArraySubscript0S', [None, None], None), 293 | Production('array-subscript', [], 294 | 'ArraySubscript1S', [], None), 295 | # 12 296 | Production('code-block', ['left-brace', 'local-define-list', 'code-list', 'right-brace'], 297 | None, [None, 'CodeBlock0C1', 'CodeBlock0C2', None], 'CodeBlock0E'), 298 | # 13 299 | Production('local-define-list', ['local-var-define', 'local-define-list'], 300 | None, ['LocalDefineList0C0', 'LocalDefineList0C1'], None), 301 | Production('local-define-list', [], 302 | None, [], None), 303 | # 14 304 | Production('local-var-define', ['type', 'id', 'var-define-follow'], 305 | None, [None, None, None], 'LocalVarDefine0E'), 306 | # 15 307 | Production('code-list', ['code', 'code-list'], 308 | None, ['CodeList0C0', 'CodeList0C1'], 'CodeList0E'), 309 | Production('code-list', [], 310 | None, [], 'CodeList1E'), 311 | # 16 312 | Production('code', ['normal-statement'], 313 | None, ['Code0C0'], 'Code0E'), 314 | Production('code', ['selection-statement'], 315 | None, ['Code1C0'], 'Code1E'), 316 | Production('code', ['iteration-statement'], 317 | None, ['Code2C0'], 'Code2E'), 318 | Production('code', ['return-statement'], 319 | None, ['Code3C0'], 'Code3E'), 320 | # Production('normal-statement', ['eval-statement', 'semicolon']), 321 | # Production('normal-statement', ['semicolon']), 322 | # 17 323 | Production('normal-statement', ['semicolon'], 324 | None, [None], 'NormalStatement0E'), 325 | Production('normal-statement', ['id', 'normal-statement-follow'], 326 | None, [None, 'NormalStatement1C1'], 'NormalStatement1E'), 327 | # 18 328 | Production('normal-statement-follow', ['var-follow', 'evaluate', 'expression', 'semicolon'], 329 | None, ['NormalStatementFollow0C0', None, 'NormalStatementFollow0C2', None], 'NormalStatementFollow0E'), 330 | Production('normal-statement-follow', ['call-follow', 'semicolon'], 331 | None, ['NormalStatementFollow1C0', None], 'NormalStatementFollow1E'), 332 | # 19 333 | Production('call-follow', ['left-parentheses', 'call-params', 'right-parentheses'], 334 | None, [None, 'CallFollow0C1', None], 'CallFollow0E'), 335 | # 20 336 | Production('call-params', ['call-param-list'], 337 | None, ['CallParams0C0'], 'CallParams0E'), 338 | Production('call-params', [], 339 | None, [], 'CallParams1E'), 340 | # 21 341 | Production('call-param-list', ['expression', 'call-param-follow'], 342 | None, ['CallParamList0C0', 'CallParamList0C1'], 'CallParamList0E'), 343 | # 22 344 | Production('call-param-follow', ['comma', 'expression', 'call-param-follow'], 345 | None, [None, 'CallParamFollow0C1', 'CallParamFollow0C2'], 'CallParamFollow0E'), 346 | Production('call-param-follow', [], 347 | None, [], 'CallParamFollow1E'), 348 | # 23 349 | Production('selection-statement', 350 | ['if', 'left-parentheses', 'expression', 'right-parentheses', 'left-brace', 351 | 'code-list', 'right-brace', 'selection-follow'], 352 | None, [None, None, 'SelectionStatement0C2', None, None, 'SelectionStatement0C5', 353 | None, 'SelectionStatement0C5'], 'SelectionStatement0E'), 354 | # 24 355 | Production('selection-follow', ['else', 'left-brace', 'code-list', 'right-brace'], 356 | None, [None, None, 'SelectionFollow0C2', None], 'SelectionFollow0E'), 357 | Production('selection-follow', [], 358 | None, [], 'SelectionFollow1E'), 359 | # 25 360 | Production('iteration-statement', ['while', 'left-parentheses', 'expression', 361 | 'right-parentheses', 'iteration-follow'], 362 | None, [None, None, 'IterationStatement0C2', None, 'IterationStatement0C4'], 'IterationStatement0E'), 363 | # 26 364 | Production('iteration-follow', ['left-brace', 'code-list', 'right-brace'], 365 | None, [None, 'IterationFollow0C1', None], 'IterationFollow0E'), 366 | Production('iteration-follow', ['code'], 367 | None, ['IterationFollow1C0'], 'IterationFollow1E'), 368 | # 27 369 | Production('return-statement', ['return', 'return-follow'], 370 | None, [None, 'ReturnStatement0C1'], 'ReturnStatement0E'), 371 | # 28 372 | Production('return-follow', ['semicolon'], 373 | None, [None], 'ReturnFollow0E'), 374 | Production('return-follow', ['expression', 'semicolon'], 375 | None, ['ReturnFollow1C0', None], 'ReturnFollow1E'), 376 | # Production('eval-statement', ['var', 'evaluate', 'expression']), 377 | # Production('var', ['id', 'var-follow']), 378 | # 29 379 | Production('var-follow', ['left-bracket', 'expression', 'right-bracket'], 380 | None, [None, 'VarFollow0C1', None], 'VarFollow0E'), 381 | Production('var-follow', [], 382 | None, [], 'VarFollow1E'), 383 | # 30 384 | Production('expression', ['additive-expr', 'expression-follow'], 385 | None, ['Expression0C0', 'Expression0C1'], 'Expression0E'), 386 | # 31 387 | Production('expression-follow', ['rel-op', 'additive-expr'], 388 | None, [None, 'ExpressionFollow0C1'], 'ExpressionFollow0E'), 389 | Production('expression-follow', [], 390 | None, [], 'ExpressionFollow1E'), 391 | # 32 392 | Production('rel-op', ['smaller-equal'], 393 | None, [None], 'RelOp0E'), 394 | Production('rel-op', ['smaller'], 395 | None, [None], 'RelOp1E'), 396 | Production('rel-op', ['bigger'], 397 | None, [None], 'RelOp2E'), 398 | Production('rel-op', ['bigger-equal'], 399 | None, [None], 'RelOp3E'), 400 | Production('rel-op', ['equal'], 401 | None, [None], 'RelOp4E'), 402 | Production('rel-op', ['not-equal'], 403 | None, [None], 'RelOp5E'), 404 | # 33 405 | Production('additive-expr', ['term', 'additive-expr-follow'], 406 | None, ['AdditiveExpr0C0', 'AdditiveExpr0C1'], 'AdditiveExpr0E'), 407 | # 34 408 | Production('additive-expr-follow', ['add-op', 'term', 'additive-expr-follow'], 409 | None, [None, 'AdditiveExprFollow0C1', 'AdditiveExprFollow0C2'], 'AdditiveExprFollow0E'), 410 | Production('additive-expr-follow', [], 411 | None, [], 'AdditiveExprFollow1E'), 412 | # 35 413 | Production('add-op', ['addition'], 414 | None, [None], 'AddOp0E'), 415 | Production('add-op', ['subtraction'], 416 | None, [None], 'AddOp1E'), 417 | # 36 418 | Production('term', ['factor', 'term-follow'], 419 | None, ['Term0C0', 'Term0C1'], 'Term0E'), 420 | # 37 421 | Production('term-follow', ['mul-op', 'factor', 'term-follow'], 422 | None, [None, 'TermFollow0C1', 'TermFollow0C2'], 'TermFollow0E'), 423 | Production('term-follow', [], 424 | None, [], None), 425 | # 38 426 | Production('mul-op', ['multiplication'], 427 | None, [None], 'MulOp0E'), 428 | Production('mul-op', ['division'], 429 | None, [None], 'MulOp1E'), 430 | # 39 431 | Production('factor', ['left-parentheses', 'expression', 'right-parentheses'], 432 | None, [None, 'Factor0C1', None], 'Factor0E'), 433 | Production('factor', ['id', 'id-factor-follow'], 434 | None, [None, 'Factor1C1'], 'Factor1E'), 435 | Production('factor', ['num'], 436 | None, [None], 'Factor2E'), 437 | # 40 438 | Production('id-factor-follow', ['var-follow'], 439 | None, [None], 'IdFactorFollow0E'), 440 | Production('id-factor-follow', ['left-parentheses', 'args', 'right-parentheses'], 441 | None, [None, 'IdFactorFollow1C1', None], 'IdFactorFollow1E'), 442 | # 41 443 | Production('args', ['arg-list'], 444 | None, ['Args0C0'], 'Args0E'), 445 | Production('args', [], 446 | None, [], 'Args1E'), 447 | # 42 448 | Production('arg-list', ['expression', 'arg-list-follow'], 449 | None, ['ArgList0C0', 'ArgList0C1'], 'ArgList0E'), 450 | Production('arg-list-follow', ['comma', 'expression', 'arg-list-follow'], 451 | None, [None, 'ArgListFollow0C1', 'ArgListFollow0C2'], 'ArgListFollow0E'), 452 | Production('arg-list-follow', [], 453 | None, [], 'ArgListFollow1E') 454 | ] 455 | 456 | # 文法开始符号 457 | grammar_start = Sign('program') -------------------------------------------------------------------------------- /syntax/syntax.py: -------------------------------------------------------------------------------- 1 | """ 2 | 语法分析 3 | """ 4 | from syntax.rule import Sign, Production, terminal_sign_type, non_terminal_sign_type, productions, grammar_start 5 | from error import SyntaxRuleError, SyntaxError, SemanticRuleError 6 | from semantic.rule import SemanticRule, SemanticError, SemanticRuleFactory 7 | 8 | 9 | class PredictingAnalysisTable: 10 | """ 11 | 预测分析表 12 | """ 13 | def __init__(self): 14 | """ 15 | 构造 16 | """ 17 | # 错误 18 | self.__error = None 19 | 20 | # 预测分析表 21 | self.__table = list() 22 | 23 | # 所有的非终结符 24 | self.__non_terminal_signs = list() 25 | # 所有的终结符 26 | self.__terminal_signs = list() 27 | 28 | # 载入所有的符号 29 | for i in non_terminal_sign_type: 30 | self.__non_terminal_signs.append(Sign(i)) 31 | for i in terminal_sign_type: 32 | self.__terminal_signs.append(Sign(i)) 33 | 34 | # 根据非终结符和终结符的数量为预测分析表分配空间,并且为每一个格子预先填上 None 35 | for i in non_terminal_sign_type: 36 | self.__table.append(list()) 37 | for i in range(0, len(non_terminal_sign_type)): 38 | for j in terminal_sign_type: 39 | self.__table[i].append(None) 40 | 41 | # 为每一个非终结符建立 first 集和 follow 集 42 | self.__firsts = list() 43 | self.__follows = list() 44 | 45 | # 为每一个非终结符的 first 集和 follow 集分配空间 46 | for i in non_terminal_sign_type: 47 | self.__firsts.append(list()) 48 | self.__follows.append(list()) 49 | 50 | def compile(self): 51 | """ 52 | 编译预测分析表 53 | """ 54 | # 对每一个文法元素求其 first 集 55 | self.__calculate_firsts() 56 | # 对每一个文法元素求其 follow 集 57 | self.__calculate_follows() 58 | # 根据 first 集和 follow 集生成预测分析表 59 | success = self.__generate_table() 60 | return success 61 | 62 | def get_production(self, non_terminal_sign, terminal_sign): 63 | """ 64 | 从预测分析表中获取产生式 65 | :param non_terminal_sign: 非终结符 66 | :param terminal_sign: 终结符 67 | :return: 产生式 68 | """ 69 | x = self.__get_non_terminal_sign_index(non_terminal_sign) 70 | y = self.__get_terminal_sign_index(terminal_sign) 71 | return self.__table[x][y] 72 | 73 | @classmethod 74 | def __set_add(cls, container, sign): 75 | """ 76 | 将 sign 添加到 container 中并返回 True,如果其中已经有该元素了则返回 False 77 | :param container: 要添加到的集合 78 | :param sign: 符号 79 | :return: 添加是否成功 80 | """ 81 | exist = False 82 | for elem in container: 83 | if elem.type == sign.type: 84 | exist = True 85 | if not exist: 86 | container.append(sign) 87 | return not exist 88 | 89 | def __get_terminal_sign_index(self, terminal_sign): 90 | """ 91 | 获取终结符的索引 92 | :param terminal_sign: 终结符 93 | :return: 索引(寻找失败返回 -1) 94 | """ 95 | for i in range(0, len(self.__terminal_signs)): 96 | if terminal_sign.type == self.__terminal_signs[i].type: 97 | return i 98 | return -1 99 | 100 | def __get_non_terminal_sign_index(self, non_terminal_sign): 101 | """ 102 | 获取非终结符的索引 103 | :param non_terminal_sign: 非终结符 104 | :return: 索引(寻找失败返回 -1) 105 | """ 106 | for i in range(0, len(self.__non_terminal_signs)): 107 | if non_terminal_sign.type == self.__non_terminal_signs[i].type: 108 | return i 109 | return -1 110 | 111 | def __get_non_terminal_sign_first(self, non_terminal_sign): 112 | """ 113 | 获取目标非终结符的 first 集的引用 114 | :param non_terminal_sign: 目标非终结符 115 | :return: 其 first 集的引用 116 | """ 117 | return self.__firsts[self.__get_non_terminal_sign_index(non_terminal_sign)] 118 | 119 | def __get_non_terminal_sign_first_no_empty(self, non_terminal_sign): 120 | """ 121 | 获取目标非终结符的 first 集的非空拷贝 122 | :param non_terminal_sign: 目标非终结符 123 | :return: 其 first 集的非空拷贝 124 | """ 125 | result = list() 126 | for i in self.__get_non_terminal_sign_first(non_terminal_sign): 127 | if not i.is_empty_sign(): 128 | result.append(i) 129 | return result 130 | 131 | def __is_empty_in_non_terminal_sign_first(self, non_terminal_sign): 132 | """ 133 | 目标非终结符的 first 集中是否有空字 134 | :param non_terminal_sign: 目标非终结符 135 | :return: True/False 136 | """ 137 | for i in self.__get_non_terminal_sign_first(non_terminal_sign): 138 | if i.is_empty_sign(): 139 | return True 140 | return False 141 | 142 | def __get_non_terminal_sign_follow(self, non_terminal_sign): 143 | """ 144 | 获取非终结符的 follow 集 145 | :param non_terminal_sign: 非终结符 146 | :return: 其 follow 集 147 | """ 148 | return self.__follows[self.__get_non_terminal_sign_index(non_terminal_sign)] 149 | 150 | def __calculate_firsts(self): 151 | """ 152 | 求所有的 first 集 153 | """ 154 | # 立一个 flag,用来标志 firsts 集是否增大 155 | flag = True 156 | # 开始循环 157 | while flag: 158 | flag = False 159 | # 在每一次循环之中遍历所有产生式 160 | for production in productions: 161 | # 如果产生式右边为空 162 | if len(production.right) == 0: 163 | # 将空字加入其 first 集 164 | if self.__set_add(self.__get_non_terminal_sign_first(production.left), Sign('empty')): 165 | flag = True 166 | # 如果产生式右边不为空 167 | else: 168 | # 如果是以终结符开头,将终结符添加到其 first 集 169 | if production.right[0].is_terminal_sign(): 170 | if self.__set_add(self.__get_non_terminal_sign_first(production.left), production.right[0]): 171 | flag = True 172 | # 如果是以非终结符开头 173 | elif production.right[0].is_non_terminal_sign(): 174 | # (1) 将开头非终结符的 first 集中的所有非空元素添加到产生式左边非终结符的 first 集中 175 | bigger = False 176 | for i in self.__get_non_terminal_sign_first_no_empty(production.right[0]): 177 | if self.__set_add(self.__get_non_terminal_sign_first(production.left), i): 178 | bigger = True 179 | if bigger: 180 | flag = True 181 | 182 | # (2) 从第一个非终结符开始循环,如果其 first 集中包含空字,那么将它下一个符号的 first 183 | # 集添加到产生式左边非终结符的 first 集中去 184 | for i in range(0, len(production.right)): 185 | if production.right[i].is_non_terminal_sign(): 186 | # 如果包含空字 187 | if self.__is_empty_in_non_terminal_sign_first(production.right[i]): 188 | # 如果它是最后一个,将空字填入 189 | if i == len(production.right) - 1: 190 | if self.__set_add(self.__get_non_terminal_sign_first(production.left), 191 | Sign('empty')): 192 | flag = True 193 | # 如果不是最后一个 194 | else: 195 | # 如果它之后是终结符 196 | if production.right[i + 1].is_terminal_sign(): 197 | if self.__set_add(self.__get_non_terminal_sign_first(production.left), 198 | production.right[i + 1]): 199 | flag = True 200 | # 如果它之后是非终结符 201 | elif production.right[i + 1].is_non_terminal_sign(): 202 | bigger = False 203 | for j in self.__get_non_terminal_sign_first_no_empty( 204 | production.right[i + 1]): 205 | if self.__set_add( 206 | self.__get_non_terminal_sign_first(production.left), j): 207 | bigger = True 208 | if bigger: 209 | flag = True 210 | else: 211 | self.__error = SyntaxRuleError('终结符或非终结符类型错误') 212 | return False 213 | # 如果不包含空字 214 | else: 215 | break 216 | else: 217 | break 218 | # 否则报错 219 | else: 220 | self.__error = SyntaxRuleError('终结符或非终结符类型错误') 221 | return False 222 | 223 | def __calculate_follows(self): 224 | """ 225 | 求所有的 follow 集 226 | """ 227 | first = list() 228 | flag = True 229 | while flag: 230 | flag = False 231 | # 遍历所有产生式 232 | for production in productions: 233 | # 如果产生式左边是开始符号 234 | if production.left.type == grammar_start.type: 235 | if self.__set_add(self.__get_non_terminal_sign_follow(production.left), Sign('pound')): 236 | flag = True 237 | 238 | # 遍历产生式右边 239 | for i in range(0, len(production.right)): 240 | # 如果是非终结符 241 | if production.right[i].is_non_terminal_sign(): 242 | # 如果它是产生式最后一个符号 243 | if i == len(production.right) - 1: 244 | # 将产生式左边非终结符的 follow 集添加到这个符号的 follow 集中 245 | bigger = False 246 | for j in self.__get_non_terminal_sign_follow(production.left): 247 | if self.__set_add(self.__get_non_terminal_sign_follow(production.right[i]), j): 248 | bigger = True 249 | if bigger: 250 | flag = True 251 | # 否则观察其之后的元素 252 | else: 253 | # 求他之后所有符号集合的 first 集 254 | first.clear() 255 | first += self.__calculate_set_first(production.right[i + 1:]) 256 | # (1) 将 first 中所有非空元素填入 follow 257 | empty_find = False 258 | for f in first: 259 | if not f.is_empty_sign(): 260 | self.__set_add(self.__get_non_terminal_sign_follow(production.right[i]), f) 261 | else: 262 | empty_find = True 263 | 264 | # (2) 如果 first 中含有空 265 | if empty_find: 266 | # 将产生式左边非终结符的 follow 集添加到这个符号的 follow 集中 267 | bigger = False 268 | for j in self.__get_non_terminal_sign_follow(production.left): 269 | if self.__set_add(self.__get_non_terminal_sign_follow(production.right[i]), j): 270 | bigger = True 271 | if bigger: 272 | flag = True 273 | 274 | # # 如果他后面是一个终结符 275 | # if production.right[i + 1].is_terminal_sign(): 276 | # if self.__set_add(self.__get_non_terminal_sign_follow(production.right[i]), 277 | # production.right[i + 1]): 278 | # flag = True 279 | # # 如果他后面是一个非终结符 280 | # elif production.right[i + 1].is_non_terminal_sign(): 281 | # # (1) 将后面非终结符的 first 集中的所有非空元素填入 282 | # bigger = False 283 | # for j in self.__get_non_terminal_sign_first_no_empty(production.right[i + 1]): 284 | # if self.__set_add(self.__get_non_terminal_sign_follow(production.right[i]), j): 285 | # bigger = True 286 | # if bigger: 287 | # flag = True 288 | # 289 | # # (2) 如果后面所有的非终结符 first 集都包含空 290 | # # 那么,则将产生式左边的 follow 集添加到该非终结符的 follow 集中去 291 | # all_empty_in_first = True 292 | # for j in range(i + 1, len(production.right)): 293 | # if not self.__is_empty_in_non_terminal_sign_first(production.right[j]): 294 | # all_empty_in_first = False 295 | # break 296 | # if all_empty_in_first: 297 | # bigger = False 298 | # for j in self.__get_non_terminal_sign_follow(production.left): 299 | # if self.__set_add(self.__get_non_terminal_sign_follow(production.right[i]), j): 300 | # bigger = True 301 | # if bigger: 302 | # flag = True 303 | # # 否则报错 304 | # else: 305 | # self.__error = SyntaxRuleError('终结符或非终结符类型错误') 306 | # return False 307 | # 如果是终结符 308 | elif production.right[i].is_terminal_sign(): 309 | continue 310 | # 否则报错 311 | else: 312 | self.__error = SyntaxRuleError('终结符或非终结符类型错误') 313 | return False 314 | 315 | def __calculate_set_first(self, container): 316 | """ 317 | 计算一系列符号的 first 集 318 | :param container: 符号集合 319 | :return: first 集 320 | """ 321 | first = list() 322 | 323 | # 开始求 first 集 324 | # 如果集合为空 325 | first = list() 326 | 327 | # 开始求 first 集 328 | # 如果产生式右边为空 329 | if len(container) == 0: 330 | # 将空字加入其 first 集 331 | self.__set_add(first, Sign('empty')) 332 | # 如果产生式右边补位空 333 | else: 334 | # 如果是以终结符开头,将终结符添加到 first 集 335 | if container[0].is_terminal_sign(): 336 | self.__set_add(first, container[0]) 337 | # 如果是以非终结符开头 338 | elif container[0].is_non_terminal_sign(): 339 | # (1) 将开头非终结符的 first 集中的所有非空元素添加到 first 中 340 | for i in self.__get_non_terminal_sign_first_no_empty(container[0]): 341 | self.__set_add(first, i) 342 | 343 | # (2) 从第一个非终结符开始循环,如果其 first 集中包含空字,那么将它的下一个符号的 first 344 | # 集添加到 first 中 345 | for i in range(0, len(container)): 346 | if container[i].is_non_terminal_sign(): 347 | # 如果包含空字 348 | if self.__is_empty_in_non_terminal_sign_first(container[i]): 349 | # 如果它是最后一个,将空字填入 350 | if i == len(container) - 1: 351 | self.__set_add(first, Sign('empty')) 352 | # 如果不是最后一个 353 | else: 354 | # 如果它之后是终结符 355 | if container[i + 1].is_terminal_sign(): 356 | self.__set_add(first, container[i + 1]) 357 | # 如果它之后是非终结符 358 | elif container[i + 1].is_non_terminal_sign(): 359 | for j in self.__get_non_terminal_sign_first_no_empty(container[i + 1]): 360 | self.__set_add(first, j) 361 | # 否则报错 362 | else: 363 | self.__error = SyntaxRuleError('终结符或非终结符类型错误') 364 | return False 365 | # 如果不含空字 366 | else: 367 | break 368 | else: 369 | break 370 | # 否则报错 371 | else: 372 | self.__error = SyntaxRuleError('终结符或非终结符类型错误') 373 | return False 374 | 375 | return first 376 | 377 | def __insert_to_table(self, production, terminal): 378 | """ 379 | 将产生式插入预测分析表对应位置 380 | :param production: 产生式 381 | :param terminal: 终结符 382 | :return: 是否插入成功 383 | """ 384 | # 先判断应该插入到的位置 385 | x = self.__get_non_terminal_sign_index(production.left) 386 | y = self.__get_terminal_sign_index(terminal) 387 | 388 | # 如果那个位置已经有产生式了 389 | if self.__table[x][y]: 390 | # 判断这个产生式是不是与要插入的产生式一样 391 | same_left = production.left.type == self.__table[x][y].left.type 392 | if same_left: 393 | same_right = True 394 | if len(production.right) != len(self.__table[x][y].right): 395 | self.__error = SyntaxRuleError("文法非LL(1)" + production.str) 396 | return False 397 | else: 398 | for i in range(0, len(production.right)): 399 | if production.right[i].type != self.__table[x][y].right[i].type: 400 | same_right = False 401 | if same_right: 402 | # 执行插入 403 | del self.__table[x][y] 404 | self.__table[x].insert(y, production) 405 | return True 406 | else: 407 | self.__error = SyntaxRuleError("文法非LL(1)" + production.str) 408 | return False 409 | else: 410 | self.__error = SyntaxRuleError("文法非LL(1)" + production.str) 411 | return False 412 | # 如果那个位置为空,说明可以填入 413 | else: 414 | # 执行插入 415 | del self.__table[x][y] 416 | self.__table[x].insert(y, production) 417 | return True 418 | 419 | @classmethod 420 | def __set_have_repeat(cls, set1, set2): 421 | """ 422 | 判断两个集合是否有交集 423 | :param set1: 集合1 424 | :param set2: 集合2 425 | :return: 是否有交集 426 | """ 427 | for i in set1: 428 | for j in set2: 429 | if i.type == j.type: 430 | return True 431 | return False 432 | 433 | def __grammar_rule_debug(self): 434 | """ 435 | 调试使用,求一个非终结符对应的所有产生式右边的 first 集中是否有相交元素 436 | """ 437 | # 一个非终结符对应的所有产生式 438 | his_productions = list() 439 | # 那些产生式对应的 first 集 440 | firsts = list() 441 | # 错误 442 | errors = list() 443 | 444 | # 对于所有的非终结符 445 | for non_terminal_sign in self.__non_terminal_signs: 446 | # 寻找他对应的所有产生式 447 | his_productions.clear() 448 | firsts.clear() 449 | for production in productions: 450 | if non_terminal_sign.type == production.left.type: 451 | his_productions.append(production) 452 | 453 | # 对于那些产生式,分别求 first 集 454 | for production in his_productions: 455 | firsts.append(self.__calculate_set_first(production.right)) 456 | 457 | # 是否有交集 458 | have_repeat = False 459 | # 查看这些产生式的 first 集两两之间是否有交集 460 | for i in range(0, len(his_productions) - 1): 461 | for j in range(i + 1, len(his_productions)): 462 | if self.__set_have_repeat(firsts[i], firsts[j]): 463 | have_repeat = True 464 | break 465 | 466 | # 如果有交集 467 | if have_repeat: 468 | errors.append('产生式 First 集重叠 ' + '非终结符: ' + non_terminal_sign.type) 469 | 470 | # 如果非终结符的 First 集中包含空字 471 | if self.__is_empty_in_non_terminal_sign_first(non_terminal_sign): 472 | # 如果他的 First 集和 Follow 集有交集 473 | if self.__set_have_repeat(self.__get_non_terminal_sign_first(non_terminal_sign), 474 | self.__get_non_terminal_sign_follow(non_terminal_sign)): 475 | errors.append('产生式 First 集和 Follow 集重叠 ' + '非终结符: ' + non_terminal_sign.type) 476 | return 477 | 478 | def __generate_table(self): 479 | """ 480 | 根据 first 集和 follow 集生成预测分析表 481 | :return: 是否生成成功 482 | """ 483 | # 调试 484 | self.__grammar_rule_debug() 485 | 486 | # 对每一条产生式应用规则 487 | for production in productions: 488 | # 先求出该产生式右边部分的 first 集 489 | first = self.__calculate_set_first(production.right) 490 | 491 | # 对每一个 first 集中的每一个终结符执行操作 492 | empty_find = False 493 | for i in list(first): 494 | if i.type == 'empty': 495 | empty_find = True 496 | else: 497 | if not self.__insert_to_table(production, i): 498 | return False 499 | 500 | # 如果其 first 集中有空字,则对 follow 集中的每一个终结符执行操作 501 | if empty_find: 502 | for i in self.__get_non_terminal_sign_follow(production.left): 503 | if not self.__insert_to_table(production, i): 504 | return False 505 | 506 | return True 507 | 508 | 509 | class Node: 510 | """ 511 | 树节点 512 | """ 513 | def __init__(self, data): 514 | """ 515 | 树节点 516 | :param data: 节点数据 517 | """ 518 | self.data = data 519 | self.str = data.type 520 | self.children = list() 521 | self.parent = None 522 | 523 | # 属性 524 | self.lexical = None 525 | self.code = list() 526 | self.type = None 527 | self.id = None 528 | self.length = None 529 | self.fun = None 530 | self.num = None 531 | self.names = list() 532 | self.bool = None 533 | self.op = None 534 | self.add = None 535 | self.mul = None 536 | 537 | def get_pre_brother(self, index): 538 | """ 539 | 获取它前 index 位的兄弟 540 | :param index: .. 541 | :return: 兄弟 542 | """ 543 | self_index = 0 544 | for i in range(0, len(self.parent.children)): 545 | if self.parent.children[i] is self: 546 | self_index = i 547 | return self.parent.children[self_index - index] 548 | 549 | 550 | class Tree: 551 | """ 552 | 树 553 | """ 554 | def __init__(self, root): 555 | """ 556 | 构造 557 | :param root: 树的根节点 558 | """ 559 | self.root = root 560 | 561 | 562 | class Stack: 563 | """ 564 | 栈 565 | """ 566 | def __init__(self): 567 | """ 568 | 构造 569 | """ 570 | self.__container = list() 571 | 572 | def push(self, elem): 573 | """ 574 | 入栈 575 | :param elem: 入栈元素 576 | """ 577 | self.__container.append(elem) 578 | 579 | def pop(self): 580 | """ 581 | 将栈顶元素出栈 582 | :return: 栈顶元素 583 | """ 584 | top = self.top() 585 | self.__container.pop() 586 | return top 587 | 588 | def top(self): 589 | """ 590 | 获取栈顶元素 591 | :return: 栈顶元素 592 | """ 593 | return self.__container[-1] 594 | 595 | def empty(self): 596 | """ 597 | 栈是否为空 598 | :return: 栈是否为空 599 | """ 600 | return len(self.__container) == 0 601 | 602 | 603 | class Syntax: 604 | """ 605 | 语法分析器 606 | """ 607 | def __init__(self): 608 | """ 609 | 构造 610 | """ 611 | # 语法树的构建 612 | self.__grammar_tree = None 613 | # 准备存放错误 614 | self.__error = list() 615 | # 预测分析表的构建 616 | self.__pa_table = PredictingAnalysisTable() 617 | # 编译预测分析表 618 | if self.__pa_table.compile(): 619 | self.__error.append(SyntaxRuleError('预测分析表编译失败')) 620 | # 准备存放词法分析的结果 621 | self.__source = list() 622 | # 将词法分析产生的 token 转换成的终结符 623 | self.__terminals = list() 624 | 625 | def put_source(self, source): 626 | """ 627 | 装填词法分析结果 628 | :param source: 词法分析结果 629 | """ 630 | self.__source.clear() 631 | self.__terminals.clear() 632 | # 装填词法分析结果 633 | for s in source: 634 | self.__source.append(s) 635 | # 将 tokens 转换成终结符 636 | for s in self.__source: 637 | self.__terminals.append(Sign(s.type, s.str, s.line)) 638 | # 在所有 tokens 的最后填入一个 # 639 | self.__terminals.append(Sign('pound')) 640 | 641 | def get_result(self): 642 | """ 643 | 获取语法树 644 | :return: 语法树 645 | """ 646 | return self.__grammar_tree 647 | 648 | def get_error(self): 649 | """ 650 | 获取错误 651 | :return: 错误 652 | """ 653 | return self.__error 654 | 655 | def execute(self): 656 | """ 657 | 执行操作 658 | :return: 语法分析是否成功 659 | """ 660 | # 新建栈 661 | stack = Stack() 662 | # 清空错误 663 | self.__error = None 664 | # 新建临时语法树 665 | grammar_tree = Tree(Node(Sign(grammar_start.type))) 666 | 667 | # 将 # 入栈 668 | stack.push(Node(Sign('pound'))) 669 | # 将语法树根节点入栈 670 | stack.push(grammar_tree.root) 671 | 672 | # 拷贝转换之后的终结符到输入串 673 | inputs = list() 674 | for sign in self.__terminals: 675 | inputs.append(sign) 676 | # 设置当前输入符号索引 677 | input_index = 0 678 | 679 | # 立下 flag 680 | flag = True 681 | while flag: 682 | # 如果栈顶是语义动作 683 | if isinstance(stack.top(), SemanticRule): 684 | stack.top().execute() 685 | if len(stack.top().errors) > 0: 686 | self.__error = stack.top().errors[-1] 687 | break 688 | else: 689 | stack.pop() 690 | # 如果栈顶是符号 691 | else: 692 | # 如果 top 是非终结符 693 | if stack.top().data.is_non_terminal_sign(): 694 | # 查看分析表 695 | production = self.__pa_table.get_production(stack.top().data, inputs[input_index]) 696 | # 如果分析表对应位置存有产生式 697 | if production: 698 | # 判断语义规则是否合法 699 | if len(production.right) != len(production.semantic_children): 700 | self.__error = SemanticRuleError('语义规则数量与产生式右边数量不一致 ' + production.str) 701 | break 702 | 703 | # 执行 start 语义 704 | semantic_start = SemanticRuleFactory.get_instance(production.semantic_start, stack.top()) 705 | if semantic_start: 706 | semantic_start.execute() 707 | if len(semantic_start.errors) > 0: 708 | self.__error = semantic_start.errors[-1] 709 | break 710 | 711 | # 将语法树按照产生式进行生长 712 | for i in range(0, len(production.right)): 713 | stack.top().children.append(Node(Sign(production.right[i].type))) 714 | stack.top().children[i].parent = stack.top() 715 | 716 | # 将 top 出栈 717 | top = stack.pop() 718 | 719 | # 将 end 语义规则入栈 720 | semantic_end = SemanticRuleFactory.get_instance(production.semantic_end, top) 721 | if semantic_end: 722 | stack.push(semantic_end) 723 | 724 | # 将 top 的孩子节点反序入栈 725 | for i in range(len(production.right) - 1, -1, -1): 726 | # for child in top.children[::-1]: 727 | stack.push(top.children[i]) 728 | semantic_child = SemanticRuleFactory.get_instance(production.semantic_children[i], 729 | top.children[i]) 730 | if semantic_child: 731 | stack.push(semantic_child) 732 | # 如果分析表中存放着错误信息 733 | else: 734 | self.__error = SyntaxError('语法错误 ' + inputs[input_index].str, inputs[input_index].line) 735 | break 736 | # 如果 top 是终结符 737 | else: 738 | # 如果 top = input 739 | if stack.top().data.type == inputs[input_index].type: 740 | # 如果 top = #,宣布分析成功 741 | if stack.top().data.type == 'pound': 742 | flag = False 743 | # 如果 top != # 744 | else: 745 | # 计算 top 的 lexical 属性 746 | stack.top().lexical = inputs[input_index].str 747 | # 将 top 出栈,让 input_index 自增 748 | stack.pop() 749 | input_index += 1 750 | # 如果 top != input 751 | else: 752 | self.__error = SyntaxError('语法错误 ' + inputs[input_index].str, inputs[input_index].line) 753 | break 754 | 755 | if self.__error: 756 | return False 757 | else: 758 | self.__grammar_tree = grammar_tree 759 | return True 760 | -------------------------------------------------------------------------------- /test.c: -------------------------------------------------------------------------------- 1 | /* A program to perform Euclid s Algorithm to compute gcd. */ 2 | int gcd(int u, int v) { 3 | if (v == 0) { 4 | return u; 5 | } else { 6 | return gcd(v, u-u/v*v); 7 | } 8 | /* u-u/v*v* == u mod v */ 9 | } 10 | 11 | void main() { 12 | int x; 13 | int y; 14 | x = input(); 15 | y = input(); 16 | output(gcd(x, y)); 17 | return; 18 | } 19 | -------------------------------------------------------------------------------- /test.py: -------------------------------------------------------------------------------- 1 | from syntax.syntax import PredictingAnalysisTable 2 | 3 | 4 | pa_table = PredictingAnalysisTable() 5 | pa_table.compile() 6 | --------------------------------------------------------------------------------