import java.awt.EventQueue;
import javax.swing.JFrame;
import javax.swing.UIManager;
public class Operator_Priority extends JFrame {
/**
*
*/
private static final long serialVersionUID = 1L;
private char VN[]={'E','T','F','P'};//非终结符
private char VT[]={'+','*','↑','i','(',')','#'};//终结符
private String[] FirstVt=new String[VN.length];//单个非终结符的first集
private String[] LastVt=new String[VN.length];
private char M[][]=new char[VT.length][VT.length];
private String G[]={"E->E+T|T","T->T*F|F","F->P↑F|P","P->(E)|i"};//文法
private String G1[]={"E->E+T|T","T->T*F|F","F->P↑F|P","P->(E)|i","E->#E#"};
private char s1[]=new char[50];
public int IsInVn(char ch) {//判断字符是否属于非终结符
int judge=999;
for(int i=0;i<VN.length;i++) {
if(ch==VN[i]) {
judge=i;
break;
}
}
return judge;
}
public int IsInVt(char ch) {//判断字符是否属于终结符
int judge=999;
for(int i=0;i<VT.length;i++) {
if(ch==VT[i]) {
judge=i;
break;
}
}
return judge;
}
public int IsInFirstVt(String s,char ch) {//判断字符是否在firstvt集中
int judge=999;
for(int i=0;i<s.length();i++) {
if(ch==s.charAt(i)) {
judge=i;
break;
}
}
return judge;
}
public String Simply(String s) {//去除重复的字符
StringBuffer sb = new StringBuffer();
int len = s.length();
int i = 0;
boolean flag = false;
for (i = 0; i < len; i++) {
char c = s.charAt(i);
if(c!='n'&&c!='u'&&c!='l') {
if (s.indexOf(c) != s.lastIndexOf(c)) {
flag = false;
}else{
flag = true;
}
if(i==s.indexOf(c))
flag=true;
if (flag) {
sb.append(c);
}
}
}
return sb.toString();
}
public boolean Check(int a[],int b[]) {//检查两个数组是否相等
int i;
int count=0;
for(i=0;i<VN.length;i++) {
if(a[i]==b[i]) {
count++;
} else {
break;
}
}
return (count==VN.length);
}
public void FirstVt_Call(char s[],int j) {//子过程
if(IsInVt(s[j])!=999) {//如果推导式后面的是终结符
FirstVt[IsInVn(s[0])]+=s[j];
} else {
if(IsInVn(s[j])!=999) {//如果后面是非终结符
FirstVt[IsInVn(s[0])]+=FirstVt[IsInVn(s[j])];
if((j+1)<s.length) {
if(IsInVt(s[j+1])!=999) {
FirstVt[IsInVn(s[0])]+=s[j+1];
}
}
}
}
}
public void Get_FirstVt() {//求解单个非终结符first集
int i,j;
for(i=0;i<G.length;i++) {
char s[]=G[i].toCharArray();
j=0;
if(IsInVn(s[j])!=999) {//如果第一个是非终结符
j=j+3;
FirstVt_Call(s,j);
while(j<s.length) {
if(s[j]=='|') {//判断|,继续后续的操作
j++;
FirstVt_Call(s,j);
} else {
j++;
}
}
}
}
}
public void FirstVt_Finally() {
int i;
int Count[]=new int[VN.length];//存放当前first集中元素的个数
int Count1[]=new int[VN.length];//存放执行后first集中元素的个数
Count[0]=1;//不等进行循环
while(Check(Count,Count1)==false) {
for(i=0;i<VN.length;i++) {
if(FirstVt[i]!=null) {
Count[i]=FirstVt[i].length();
} else {
Count[i]=0;
}
}
Get_FirstVt();
for(i=0;i<VN.length;i++) {
if(FirstVt[i]!=null) {
FirstVt[i]=Simply(FirstVt[i]);
}
}
for(i=0;i<VN.length;i++) {
if(FirstVt[i]!=null) {
Count1[i]=FirstVt[i].length();
} else {
Count1[i]=0;
}
}
}
}
public void LastVt_Call(char s[],int j) {
if(j<s.length&&s[j]!='|') {
while(j<s.length&&s[j]!='|') {
j++;
}
}
j-=1;
if(IsInVt(s[j])!=999) {//是终结符
LastVt[IsInVn(s[0])]+=s[j];
} else {
if(IsInVn(s[j])!=999&&IsInVt(s[j-1])!=999) {//如果满足P=>...aQ的形式
LastVt[IsInVn(s[0])]+=s[j-1];
} else {
if(IsInVn(s[j])!=999) {
LastVt[IsInVn(s[0])]+=LastVt[IsInVn(s[0])]+LastVt[IsInVn(s[j])];
}
}
}
}
public void Get_LastVt() {//求解单个非终结符first集
int i,j;
for(i=0;i<G.length;i++) {
char s[]=G[i].toCharArray();
j=0;
if(IsInVn(s[j])!=999) {//如果第一个是非终结符
j=j+3;
LastVt_Call(s,j);
while(j<s.length) {
if(s[j]=='|') {//判断|,继续后续的操作
j++;
LastVt_Call(s,j);
} else {
j++;
}
}
}
}
}
public void LastVt_Finally() {
int i;
int Count[]=new int[VN.length];//存放当前first集中元素的个数
int Count1[]=new int[VN.length];//存放执行后first集中元素的个数
Count[0]=1;//不等进行循环
while(Check(Count,Count1)==false) {
for(i=0;i<VN.length;i++) {
if(LastVt[i]!=null) {
Count[i]=LastVt[i].length();
} else {
Count[i]=0;
}
}
Get_LastVt();
for(i=0;i<VN.length;i++) {
if(LastVt[i]!=null) {
LastVt[i]=Simply(LastVt[i]);
}
}
for(i=0;i<VN.length;i++) {
if(LastVt[i]!=null) {
Count1[i]=LastVt[i].length();
} else {
Count1[i]=0;
}
}
}
}
void Get_Mtable() {
int i,j,k;
for(i=0;i<G1.length;i++) {//对每条产生式
char s[]=G1[i].toCharArray();
for(j=3;j<s.length-1;j++) {
if(IsInVt(s[j])!=999&&IsInVt(s[j+1])!=999) {
M[IsInVt(s[j])][IsInVt(s[j+1])]='=';
}
if(j<=(s.length-3)&&(IsInVt(s[j])!=999)&&(IsInVn(s[j+1])!=999)&&(IsInVt(s[j+2])!=999)) {
M[IsInVt(s[j])][IsInVt(s[j+2])]='=';
}
if(IsInVt(s[j])!=999&&IsInVn(s[j+1])!=999) {
for(k=0;k<FirstVt[IsInVn(s[j+1])].length();k++) {
M[IsInVt(s[j])][IsInVt(FirstVt[IsInVn(s[j+1])].charAt(k))]='<';
}
}
if(IsInVn(s[j])!=999&&IsInVt(s[j+1])!=999) {
for(k=0;k<LastVt[IsInVn(s[j])].length();k++) {
M[IsInVt(LastVt[IsInVn(s[j])].charAt(k))][IsInVt(s[j+1])]='>';
}
}
}
}
}
public char Get_Vn(String s) {
int i=0,j=3;
char N='N';
String str;
while(i<G.length) {
j=3;
while(j<G[i].length()) {
str="";
while((j<G[i].length())&&(G[i].charAt(j)!='|')) {
str+=G[i].charAt(j);
j++;
}
if(s.equals(str)) {
N=G[i].charAt(0);
break;
} else {
j++;
}
}
if(N!='N') {
break;
} else {
i++;
}
}
return N;
}
public void Print_S(int k) {
int i;
StringBuilder st=new StringBuilder();
for(i=1;i<=k;i++) {
if(s1[i]!=' ') {
st.append(s1[i]);
}
}
System.out.println(st.toString());
}
public void Get_Run() {
char Q,N;
int k=1,j;
s1[k]='#';
int h;
String s="i*i+i#";
int i=-1;
do {
i++;
if(IsInVt(s1[k])!=999) {
j=k;
} else {
j=k-1;
}
while(M[IsInVt(s1[j])][IsInVt(s.charAt(i))]=='>') {
do {
Q=s1[j];
if(IsInVt(s1[j-1])!=999) {
j=j-1;
} else {
j=j-2;
}
} while(M[IsInVt(s1[j])][IsInVt(Q)]!='<');
String s2="";
for(h=j+1;h<=k;h++) {
s2+=s1[h];
}
Print_S(k);
N=Get_Vn(s2);
k=j+1;
s1[k]=N;
Print_S(k);
}
if(M[IsInVt(s1[j])][IsInVt(s.charAt(i))]=='<'||M[IsInVt(s1[j])][IsInVt(s.charAt(i))]=='=') {
k=k+1;
s1[k]=s.charAt(i);
} else {
System.out.print("Error");
}
} while(s.charAt(i)!='#');
}
public void Print() {
for(int i=0;i<FirstVt.length;i++) {
System.out.println(FirstVt[i]);
}
}
public void Print1() {
for(int i=0;i<LastVt.length;i++) {
System.out.println(LastVt[i]);
}
}
public void Print2() {
for(int i=0;i<VT.length;i++) {
System.out.print(i+" ");
for(int j=0;j<VT.length;j++) {
System.out.print(M[i][j]+" ");
}
System.out.println();
}
}
Operator_Priority() {
FirstVt_Finally();
LastVt_Finally();
Get_Mtable();
Print();
Print1();
Print2();
Get_Run();
}
public static void main(String args[]) {
try {//使用默认窗口形式
UIManager
.setLookAndFeel("com.sun.java.swing.plaf.nimbus.NimbusLookAndFeel");
} catch (Throwable e) {
e.printStackTrace();
}
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
Operator_Priority alr = new Operator_Priority();
alr.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
alr.setBounds(300,200,400,400);
//alr.setVisible(true);
} catch (Exception e) {
e.printStackTrace();
}
}
});
}
}
Java编译原理写算符优先算法
最新推荐文章于 2022-11-04 20:50:33 发布