构造识别规范句型活前缀DFA的源代…

来源:互联网 发布:滴定分析实验数据 编辑:程序博客网 时间:2024/06/15 06:17

#include
#include
#include
#include
#include
#include
#include
using namespace std;
#define PROJECT_SET_SIZE20  
#define PROJECT_ID_POS 0
#define GRAMMER_ID_POS 1
#define GRAMMER_START_CHAR_POS 5
#define BFCHAR_POS 2
#define AFCHAR_POS 3
#define PROJECT_LEN_POS 4
#define ID 10000
char st[20][30]; 
int r;

struct grammer
{
 char **g;
 char vt[127];
 char vn[27];
 char s;
 int line;
};

typedef struct
{
 int id;
 char ch;
}SElemType;


struct gprjt
{
 char **gp;
 char s;
 int line;
};

typedef struct prjset
{
 int id;
 struct prjset *next;
 char prjt[PROJECT_SET_SIZE+1];
 char pointafter[PROJECT_SET_SIZE+1];
 struct prjset *actorgo[PROJECT_SET_SIZE];
 char pointbefore;
}prjset,*pprjset;

struct head
{
 prjset *I;
 prjset *tail;
 int size;
};


char DOT = '~';
grammer g;
gprjt project;
head root;
void Input();
int OpenFile(char *s);
void CreateProjectSet();
void Closure(prjset *prjset);
int go(int rk, prjset *prjset);
void PrintPojectSet();
int IsInSet(char *s, char ch);
void JoinSet(char *s, char ch);
void main()
{
 for(;;){   
    r=1;
   cout<<"请输入文法规则(以#作为结尾):"<<endl;
   for(;;){
     string z;
   cin>>z;
   int m=0;
   int w=0;
   for(;m
   if(z[m]=='#'){w=1;break; }
    st[r][m]=z[m];
   }
  st[r][m]='@'; 
   r=r+1;
   if(w==1) break;
    }
   st[0][0]=st[1][0];st[0][1]='-';st[0][2]='>';st[0][3]=st[1][0];st[0][4]='@';
 int count;
 int i;
 int j;
 count = r;
 g.line=count;
 g.g=(char **)malloc(sizeof(char *)*g.line);
 for(i=0; i
 {
    g.g[i]=(char *)malloc(21);
  g.g[i][0] = i;
  g.g[i][1] = 0;
 }
 for(int x=0;x
  
  j = 2;
  for(inty=0;st[x][y]!='@';y++)
   
   if(st[x][y]=='-'&& st[x][y+1]=='>'){y=y+1;continue;}
     else
     {
    charch=st[x][y];
    g.g[x][j] =ch;
   g.g[x][1]++;
   j++;  
      
  }
 }
 g.vn[0] = g.vt[0] = 0;
 for(i=0; i
 {
  for(j=2; j<=g.g[i][1]+1;j++)
  {
   if(g.g[i][j]>='A'&& g.g[i][j]<='Z')
    JoinSet(g.vn,g.g[i][j]);
   else
    JoinSet(g.vt,g.g[i][j]);
  }
 }
 g.s = g.vn[1];
 count = 0;
 for(i=0; i
  count += g.g[i][1];
 if((project.gp=(char **)malloc(sizeof(char*)*count)) == NULL)exit(1);
 int k;
 int pointpos;
 int m;
 int n;
 k = 0;
 for(i=0; i
 {
  pointpos =GRAMMER_START_CHAR_POS + 1;
  for(j=0; j
  {
   if((project.gp[k]=(char*)malloc(6+g.g[i][1])) ==NULL)exit(1);   
   project.gp[k][PROJECT_ID_POS]= k;
   project.gp[k][GRAMMER_ID_POS]= i;
   project.gp[k][PROJECT_LEN_POS]= g.g[i][1]+1;
   project.gp[k][GRAMMER_START_CHAR_POS]= g.g[i][2];
   n = 3;
   for(m=GRAMMER_START_CHAR_POS+1;m
   {
    project.gp[k][m]= g.g[i][n];
    n++;
   }
   project.gp[k][pointpos]= DOT;
  
   for(m=pointpos+1;m<=project.gp[k][PROJECT_LEN_POS]+PROJECT_LEN_POS; m++)
   {
    project.gp[k][m]= g.g[i][n];
    n++;
   }
   if(pointpos==project.gp[k][PROJECT_LEN_POS]+PROJECT_LEN_POS)
   {
    project.gp[k][AFCHAR_POS]= '\0';
   }
   else
   {
    project.gp[k][AFCHAR_POS]= project.gp[k][pointpos+1];
   }
   if(pointpos==GRAMMER_START_CHAR_POS+1)
   {
    project.gp[k][BFCHAR_POS]= '\0';
   }
   else
   {
    project.gp[k][BFCHAR_POS]= project.gp[k][pointpos-1];
   }
   pointpos++;
   k++;
  }
 }
 project.s = g.s;
 project.line = k;
 cout<<"输出拓广文法:"<<"\n";
 for(i=0; i
 {
  cout<<'('<<i+1<<')';
  for(j=2; j<=g.g[i][1]+1;j++)
  {
   if(j ==3)
    cout<<"->";
   cout<<g.g[i][j];
  }
  cout<<"\n";
 }
 cout<<"输出项目集:"<<"\n";
 cout<<"--------------------------------------\n";
 for(i=0; i
 {
  cout<<'('<<i+1<<')';
  for(j=GRAMMER_START_CHAR_POS;j<=project.gp[i][PROJECT_LEN_POS]+PROJECT_LEN_POS; j++)
  {
   if(j==GRAMMER_START_CHAR_POS+1)
    cout<<"->";
   if(project.gp[i][j]== DOT)
    cout<<"·";
   else
    cout<<project.gp[i][j];
  }
  cout<<"\n";
 }
 cout<<"--------------------------------------\n";
 cout<<"\n";
   CreateProjectSet();
   PrintPojectSet();

 for(;;)
 {
 pprjset p;
 p=root.I;
 cout<<"输入字符串,判断其是否为当前文法的活前缀:";
 string u;cin>>u;
 int v[100]={0};
 int s=1;
 int k=0;
    for(inte=0;e
             int t=0;
    for(i=1;i<=p->pointafter[0]; i++)
      {
    if(p->pointafter[i]==u[e]) { v[s]=p->actorgo[i-1]->id-ID;  s++;  p=p->actorgo[i-1];  t=1;break;}
      }
    if(t==0) { k=1;break;}
      }
    if(k==0){cout<<"该字符串为该文法的活前缀"<<"\n";
             cout<<"其路径为:";
      for(intj=0;j
      {cout<<"I"<<v[j];
         if(j!=s-1) cout<<"->";
        }
     cout<<"\n";
    }
   elsecout<<"该字符串不是该文法的活前缀"<<"\n";
  cout<<"继续输入字符串?(输入N停止输入,输入其他字符继续)";
   char q;cin>>q;
   if(q=='N') break;
 }
 }
}

void CreateProjectSet()
{
 int i;
 int j;
 int k;
 int id = ID;
 pprjset p,q;
 root.I = root.tail = NULL;
 if((p = (pprjset)malloc(sizeof(prjset))) == NULL)exit(1);
 p->id = id;
 p->next = NULL;
 p->prjt[0] = 0;
 p->pointafter[0] = 0;
 p->pointbefore = '\0';
 for(j=0; j
  p->actorgo[j] = NULL;
 for(j=0; j
  p->actorgo[j] = NULL;
 root.I = p;
 root.tail = p;
 root.size = 1;
 for(i=0; i
 {
  if(project.s ==project.gp[i][GRAMMER_START_CHAR_POS] && DOT ==project.gp[i][GRAMMER_START_CHAR_POS+1])
  {
   JoinSet(root.I->prjt,project.gp[i][PROJECT_ID_POS]);
   JoinSet(root.I->pointafter,project.gp[i][AFCHAR_POS]);
   break;
  }
 }
 Closure(root.I);
 int pos;
 for(q=root.I; q!=NULL; q=q->next)
 {
  for(i=1;i<=q->pointafter[0]; i++)
  {
   pos =i;
   pos--;
   if((p =(pprjset)malloc(sizeof(prjset))) == NULL)exit(1);  
   p->next =NULL;
   p->prjt[0]= 0;
   p->pointafter[0]= 0;
   p->pointbefore= q->pointafter[i];
   for(j=0;j
    p->actorgo[j]= NULL;
   for(j=1;j<=q->prjt[0]; j++)
   {
    if(project.gp[q->prjt[j]][AFCHAR_POS]== p->pointbefore)
     go(q->prjt[j],p);
   }
   Closure(p);
   pprjsetptr;
   intflag;
   intflagsame;
   flagsame =1;
   flag =1;
   for(ptr=root.I;ptr!=NULL; ptr=ptr->next)
   {
    flag= 1;
    if(p->prjt[0]== ptr->prjt[0])
    {
     for(k=1;k<=p->prjt[0]; k++)
     {
      if(!IsInSet(ptr->prjt,p->prjt[k]))
      {
       flag= 0;
       break;
      }//if      
     }//for
     
    }//if
    else
    {
     flag=0;     
    }//else
    if(flag== 0)
     flagsame= 0;
    else
    {
     flagsame= 1;
     break;
    }
   }//for
   if(flagsame)//flagsame== 1 , 有与*p相同的项目集,删除*p
   {
    q->actorgo[i-1]= ptr;
    free(p);
   }
   else//将p挂到root.tail
   {
    q->actorgo[i-1]= p;
    p->id= ++id;
    root.tail->next= p;
    root.tail= p;
    root.size++;
   }

  }//for
 }//for
}//CreateProjectSet


void Closure(prjset *pset)
{//rk 为项目的编号,prjset指向项目集
 int i;
 int j;
 int rk;
 
 for(i=1; i<=pset->prjt[0]; i++)
 {
  rk = pset->prjt[i];
  if(IsInSet(g.vn,project.gp[rk][AFCHAR_POS]))//若圆点后字符为vn
  {
   for(j=0;j
   {
    if(project.gp[j][GRAMMER_START_CHAR_POS]== project.gp[rk][AFCHAR_POS] &&project.gp[j][GRAMMER_START_CHAR_POS+1] == DOT)
    {
     JoinSet(pset->prjt,project.gp[j][PROJECT_ID_POS]);
     JoinSet(pset->pointafter,project.gp[j][AFCHAR_POS]);
    }//if
   }//for
  }//if
 }//for 
}//Closure

 

int go(int rk, pprjset prjset)
{//rk为项目编号,将rk的去向加入prjset指向的项目集中,返回项目编号,若无,返回-1
 int i;
 int j;
 int rksize;
 char rkS;
 char rkpointafter;
 if((rkpointafter = project.gp[rk][AFCHAR_POS]) =='\0')
 {
  return-1; 
 }
 int pointpos;
 pointpos =IsInSet(&project.gp[rk][PROJECT_LEN_POS], DOT);
 pointpos += PROJECT_LEN_POS;
 rksize = project.gp[rk][PROJECT_LEN_POS];
 rkS =project.gp[rk][GRAMMER_START_CHAR_POS];
 
 for(i=0; i
 {
  if(project.gp[i][GRAMMER_START_CHAR_POS]== rkS && project.gp[i][PROJECT_LEN_POS] == rksize&& project.gp[i][BFCHAR_POS] == rkpointafter)
  {
   intflag;
   flag =1;
   for(j=pointpos+2;j<=project.gp[i][PROJECT_LEN_POS]+PROJECT_LEN_POS; j++)
   {
    if(project.gp[i][j]!= project.gp[rk][j])
    {
     flag= 0;
     break;
    }
   }//for
   if(flag)
   {
    JoinSet(prjset->prjt,project.gp[i][PROJECT_ID_POS]);//将项目加入项目集
    if(project.gp[i][AFCHAR_POS]!= '\0')
    {JoinSet(prjset->pointafter,project.gp[i][AFCHAR_POS]);}//将项目圆点后的字符加入
    returnproject.gp[i][PROJECT_ID_POS];
   }//if
   else
    return-1;
  }//if
 }//for
}//go


void PrintPojectSet()
{
 pprjset p;
 int rk;
 int i;
 int j;
 cout<<"输出识别活前缀的DFA\n";
 for(p=root.I; p!=NULL; p=p->next)
 {
  cout<<"---------------------\n";
  cout<<'I'<<p->id-ID<<"\n";
  for(j=1; j<=p->prjt[0];j++)
  {
   rk =p->prjt[j];
   for(i=GRAMMER_START_CHAR_POS;i<=project.gp[rk][PROJECT_LEN_POS]+PROJECT_LEN_POS; i++)
   {
    if(i==GRAMMER_START_CHAR_POS+1)
     cout<<"->";
    if(project.gp[rk][i]== DOT)
     cout<<"·";
    else
     cout<<project.gp[rk][i];
   }//for
   cout<<"\n";
  }//for
  cout<<"\n";
  for(i=1;i<=p->pointafter[0]; i++)
  {
   cout<<"出度:"<<p->pointafter[i]<<"指向->"<<"I"<<p->actorgo[i-1]->id-ID<<"\n";
  }//for
 }//for
 cout<<"---------------------\n";
}//PrintPojectSet

 

int IsInSet(char *s, char ch)
{
 int i;
 for(i=1; i<=s[0]; i++)
 {
  if(s[i] == ch) return i;
 }
 return 0;
}

void JoinSet(char *s, char ch)
{
 int i;
 if(!IsInSet(s,ch))
 {
  s[0]++;
  i = s[0];
  s[i] = ch;
 }
}

0 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 儿童自己坐飞机怎么办手续 两岁宝宝发烧怎么办 网上购票待核验怎么办 老人坐飞机找不到登机口怎么办 儿童不能值机怎么办 飞机上旅客刁难怎么办 飞机上婴儿哭闹怎么办 飞机上婴儿啼哭怎么办 飞机儿童陪护手续怎么办 孕妇感冒鼻子堵怎么办 孕妇用了眼药水怎么办 孕妇用眼药水了怎么办 错过了登机时间怎么办 过了登机时间怎么办 孩子不喜欢做作业怎么办 宝宝腿不一样粗怎么办 一个小腿肿了怎么办 左右小腿不一样粗怎么办 小孩不敢自己睡怎么办 小孩不一个人睡怎么办 晚上一个人睡觉害怕怎么办 孩子自己睡害怕怎么办 小孩晚上睡觉怕怎么办 小孩分房睡害怕怎么办 坐飞机不认识字怎么办 科目一不识字怎么办 孩子不自己睡觉怎么办 70岁老人坐高铁怎么办 八岁儿童怎么办护照 第一次坐飞机有点紧张怎么办 坐飞机恐高耳鸣怎么办 火车坐过站怎么办 凌晨的火车应该怎么办 高铁坐过一站怎么办 宝宝断奶瘦了怎么办 第一次坐飞机怕晕机怎么办 焦虑症怕坐飞机怎么办 新生宝宝老是哭闹怎么办 宝宝坐飞机后哭闹怎么办 飞机经济舱不支持退票怎么办 证件被单位扣押怎么办