# 求first集中第一部分:针对->直接推出第一个字符为终结符部分 defgetFirst(self): for line in self.grammar: part_begin = line.split("->")[0] part_end_temp = line.split("->")[1] part_end = part_end_temp.split(" ") ifnot isnonterminal(part_end[0]): self.FIRST[part_begin].append(part_end[0])
# 求first第二部分:针对A -> B型,把B的first集加到A的first集合中 defgetFirst_2(self): for line in self.grammar: part_begin = line.split("->")[0] part_end_temp = line.split("->")[1] part_end = part_end_temp.split(" ") # 如果型如A -> B:则把B的first集加到A的first集中去 if isnonterminal(part_end[0]): for i inrange(0, len(part_end)): ifnot isnonterminal(part_end[i]): self.FIRST[part_begin].append(part_end[i]) break list_remove = self.FIRST.get(part_end[i]).copy() if'ε'in list_remove and i isnotlen(part_end) - 1: list_remove.remove('ε') self.FIRST[part_begin].extend(list_remove) if'ε'notin self.FIRST[part_end[i]]: break
defgetFirst_3(self): while1: test = self.FIRST self.getFirst_2() # 去除重复项 for i, j in self.FIRST.items(): temp = [] for word inlist(set(j)): temp.append(word) self.FIRST[i] = temp if test == self.FIRST: break
defgetFOLLOW_3(self): while1: test = self.FOLLOW self.getFollow() # 去除重复项 for i, j in self.FOLLOW.items(): temp = [] for word inlist(set(j)): temp.append(word) self.FOLLOW[i] = temp if test == self.FOLLOW: break
# 计算follow集的第一部分,先计算 S -> A b 类型的 defgetFollow(self): for line in self.grammar: part_begin = line.split("->")[0] part_end_temp = line.split("->")[1] part_end = part_end_temp.split(" ") if part_begin == "<G>": pass # 如果是 S->a 直接推出终结符 则 continue iflen(part_end) == 1andnot isnonterminal(part_end[0]): continue # 否则执行下面的操作 else: # 将->后面的倒序 part_end.reverse() # 最后一个为非终结符 if isnonterminal(part_end[0]):
for i inrange(0, len(part_end)): ifnot isnonterminal(part_end[i]): break self.FOLLOW[part_end[i]].extend(self.FOLLOW.get(part_begin)) if'ε'notin self.FIRST[part_end[i]]: break