编译原理语法分析(java)

来源:互联网 发布:哪个软件下载最快 编辑:程序博客网 时间:2024/05/16 08:37

今天老师要让我们写一个语法分析器,,布置的内容是,给一个已经消除了左递归和回溯的文法,

让我们写出整个语法分析过程,,我竟然记错了,,花了几个小时写了个,消除左递归


《直接递归的消除》  时间有点紧,写的有点乱,(关键是没按照命名标准来命名),以后再改吧,,没用什么数据结构,都是java内部lang.string中的方法,

若有道友写出C语言版本的,可以分享出来(谢谢)

《循环左递归》以后再写,时间好紧

文件:D:\\text.txt

内容:(可以自行修改),我是按照这个来的,,其他的也都可以

E=E+T/T
T=T*F/F
F=(E)/i


结果:

O=+TO/ε
E=TO
K=*FK/ε
T=FK
F=(E)/i

import java.io.BufferedReader;import java.io.FileInputStream;import java.io.InputStreamReader;import java.util.ArrayList;import java.util.HashMap;public class yufafenxi {public yufafenxi() {// TODO Auto-generated constructor stubtry {readFile();} catch (Exception e) {// TODO Auto-generated catch blocke.printStackTrace();}}int length=0;//读取文件,得到每行的内容public ArrayList<String> readFile() throws Exception{FileInputStream fileInputStream=new FileInputStream("D:\\text.txt");InputStreamReader reader=new InputStreamReader(fileInputStream);BufferedReader bufferedReader=new BufferedReader(reader);String text=null;ArrayList<String> all=new ArrayList<>();while((text=bufferedReader.readLine())!=null){all.add(text);}length=all.size();return all;}//得到P非终结字符的字符数组{S T F}public char[] getP(ArrayList<String> list){char[] state=new char[1024];for(int i=0;i<list.size();i++){String current=list.get(i);state[i]=current.toCharArray()[0];//得到状态S T F}return state;}//得到候选集合{E+T,T,T*F,F,(E),i}public ArrayList<String> getHouxuanstring(ArrayList<String> list){ArrayList<String> houxuanAll=new ArrayList<>();for(int i=0;i<list.size();i++){String current=list.get(i);String waitcurrent=current.substring(2, current.length());houxuanAll.add(waitcurrent);}return houxuanAll;}//得到候选分割的集合{E+T,T}{T*F,F}{(E),i}public String[] getJihe(String text){String waitcurrent=text.substring(2, text.length());String[] currentAll=waitcurrent.split("/");//得到候选式存入字符串数组return currentAll;}//得到原始首符集{E,T,T,F,(,i}public HashMap<Integer, String> getHouxuanshi(ArrayList<String> list){HashMap<Integer, String>map=new HashMap<>(); for(int i=0;i<list.size();i++){String current=list.get(i);String waitcurrent=current.substring(2, current.length());String[] currentAll=waitcurrent.split("/");//得到候选式存入字符串数组,,后续会转变为字符数组String word="";for(int j=0;j<currentAll.length;j++){word+=currentAll[j].charAt(0);//得到首位字符}map.put(i,word);//得到首符集,每行的首字符(合起来存为一个字符串,以后可以分割)}return map;}/** * P与原始首符集匹配,相等则存在左递归,消除左递归,生成新的文法 * @param p 文法左端非终结符 * @param map p的first集合 * @param list 每行的文法 */public ArrayList<String> removeLeftDigui(char[] p,HashMap<Integer, String> map,ArrayList<String> list){ArrayList<String> newList=new ArrayList<>();String longText="";String aChange="";//先比较左端非终结符和各自的FIRSE集合,此处为一对多的匹配char[] needChar={'Q','W','P','L','M','N','K','O'};//新的左端非终结符//生成新的文法是,每次从中拿一个作为左端非终结符ArrayList<String> Char=new ArrayList<>();for(int i=0;i<needChar.length;i++){Char.add(needChar[i]+"");}for(int i=0;i<length;i++){//再次循环达到一对F(1)匹配,一对F(2)匹配...char[] houxuanshi=map.get(i).toCharArray();//每行的first集合String houxuanText=new String(houxuanshi);char use=Char.get(Char.size()-1).charAt(0);//新的非终结符Char.remove(Char.size()-1);//移除已经用过的字符String hang=list.get(i);//i行的文法for(int j=0;j<houxuanshi.length;j++){//i行存在左递归,则if(houxuanText.contains(p[i]+"")){String[] allHouxuanshi=getJihe(hang);/** * 候选式FIRSE与P的比较  * 1:不相同 * 2:相同 */if(p[i]==houxuanshi[j]){/** * 生成新的候选式,如E+T * +T——>allHouxuanshi[j].substring(1, allHouxuanshi[j].length()) * O——>use * longText为新生成的一行文法 */String newText=allHouxuanshi[j].substring(1, allHouxuanshi[j].length())+use;longText=longText+newText+"/";}if(p[i]!=houxuanshi[j]){String newText=allHouxuanshi[j]+use;aChange=aChange+newText+"/";}}}if(longText.equals(""))continue;//新文法存入list中//得到新生成的文法行,候选式中需要添加空字符String AllLongText=use+"="+longText+"ε";newList.add(AllLongText);/** * 两个字符串变量每经一轮循环都置空,因为已经生成了一行新的文法 * 下一轮循环会生成新的文法,所以需要置空 */AllLongText="";longText="";//得到改变的文法行,候选式中不需要空字符String AllaChange=p[i]+"="+aChange;newList.add(AllaChange);/** * 同上 */AllaChange="";aChange="";//将存在左递归的行置空,省下来的都是不存在左递归的行,直接添加到新文法中list.set(i, "");}//去掉最后的/字符for(int i=0;i<newList.size();i++){String CurrentElement=newList.get(i);if(CurrentElement.endsWith("/")){CurrentElement=CurrentElement.substring(0, CurrentElement.length()-1);newList.set(i, CurrentElement);}}//将不存在左递归的行,添加到新文法for(int i=0;i<list.size();i++){if(!list.get(i).equals("")){newList.add(list.get(i));}}return newList;}//输出新的文法public void printNewWenfa(ArrayList<String> arrayList){for(int i=0;i<arrayList.size();i++){System.out.println(arrayList.get(i));}}public static void main(String[] args) throws Exception {yufafenxi yufafenxi=new yufafenxi();//初始化程序ArrayList<String> list=yufafenxi.readFile();//读取文件,得到所有行的字符串char[] p=yufafenxi.getP(list);//得到左端非终结符yufafenxi.getHouxuanstring(list);//得到候选集合(未使用)HashMap<Integer, String> map=yufafenxi.getHouxuanshi(list);//得到首符集即各行的FIRST集合ArrayList<String> arrayList=yufafenxi.removeLeftDigui(p, map, list);//消除直接左递归yufafenxi.printNewWenfa(arrayList);//打印新的文法}}



0 0
原创粉丝点击