python|编译原理 实验一(简单词法分析)

一、实验目的
了解词法分析程序的基本构造原理,掌握词法分析程序的手工构造方法。
二、实验内容
1、了解编译程序的词法分析过程。
2、根据PASCAL语言的说明语句形式,用手工方法构造一个对说明语句进行词法分析的程序。该程序能对从键盘输入或从文件读入形如:
“const count=10,sum=81.5, char1=’f’, string1=”hj”,max=169; ”
的常量说明串进行处理,分析常量说明串中各常量名、常量类型及常量值,并统计各种类型常量个数。
三、实验要求
1、输入的常量说明串,要求最后以分号作结束标志;
2、根据输入串或读入的文本文件中第一个单词是否为“const”判断输入串或文本文件是否为常量说明内容;
3、识别输入串或打开的文本文件中的常量名。常量名必须是标识符,定义为字母开头,后跟若干个字母,数字或下划线;
4、根据各常量名紧跟等号“=”后面的内容判断常量的类型。其中:字符型常量定义为放在单引号内的一个字符;字符串常量定义为放在双引号内所有内容;整型常量定义为带或不带+、- 号,不以0开头的若干数字的组合;实型常量定义为带或不带+、- 号,不以0开头的若干数字加上小数点再后跟若干数字的组合;
【python|编译原理 实验一(简单词法分析)】5、统计并输出串或文件中包含的各种类型的常量个数;
6、以二元组(类型,值)的形式输出各常量的类型和值;
7、根据常量说明串置于高级语言源程序中时可能出现的错误情况,模仿高级语言编译器对不同错误情况做出相应处理;

import sys import rekeywords = ['const']def to_split(str): str = str.strip() f = 0 while True: if str[-1] == '; ': str = str[:-1] f = 1 else: if f == 1: break else: print("末尾缺少; \n") sys.exit()# str_list = str.split(',') all = re.finditer(',[^\"\'=]{1,100}=', str) list_dou = [] for i in all: list_dou.append(i.span()[0]) str2 = list(str) a = "" for i in range(len(str)): if i in list_dou: a = a + '!@#123$%^&*' else: a = a + str[i] str = a.split('!@#123$%^&*') return strdef get_type(str): str = str.strip() global int_num global char_num global string_num global float_numname_word = "" type_word = "" value_word = ""# p判断是否有 = 号,如果有的话输出下标 index_dengyu = str.find("=") if index_dengyu == -1: print("缺少 = \n") sys.exit() #= 号左右分割 str_left = str[:index_dengyu].strip() str_right = str[index_dengyu + 1:].strip() #= 号左分割成单词# =左边按空格分隔,去掉列表里面的'',然后判断 str_left_list = str_left.split(' ') temp = [] for i in str_left_list: if i != '': temp.append(i) str_left_list = tempif len(str_left_list) == 1: name_word = str_left_list[0] # 判断第一个是否为字母 if name_word[0].isalpha() is False: print("%s(错误!变量名首字母不为字母!)\n" % str_left_list[0]) return 0 elif len(str_left_list) == 2: if str_left_list[0] in keywords: name_word = str_left_list[1] if name_word[0].isalpha() is False: print("%s(错误!变量名首字母不为字母!)\n" % str_left_list[1]) return 0 else: print("%s 不是关键字!\n" % str_left_list[0]) sys.exit(); # 格式 if str_right[0] == '.': type_word = "float" float_num = float_num + 1 value_word = str_right elif str_right[0] == '\'' and str_right[-1] == '\'': if len(str_right) != 3: print("%s(错误!字符串格式错误!)\n" % name_word) return 0 type_word = "char" char_num = char_num + 1 value_word = str_right else: try: try: type_word = "integer" value_word = int(str_right) int_num = int_num + 1 except: type_word = "float" value_word = float(str_right) float_num = float_num + 1 except: if str_right[0] != '\"' and str_right[-1] != '\"': print("%s(错误!字符串格式错误!)\n" % name_word) return 0 type_word = "string" string_num = string_num + 1 value_word = str_right print("%s(%s,%s)\n" % (name_word, type_word, value_word))str = """ const count1 = 2180,sum1 = 6881.655,char1='f', count2=65,max1=169,char2='@',sum2=.0815,str1="\"cds f 89h\"", max2=1.6229,str2="good jbhn"; """str_list = to_split(str)int_num = 0 char_num = 0 string_num = 0 float_num = 0# str_list = ["const count1 = 2180"] for i in str_list: get_type(i) print(("int_num = %s,char_num = %s,string_num = %s,float_num = %s\n" \ % (int_num, char_num, string_num, float_num)))


    推荐阅读